紫書-第五章-例題
衹爲總結,不爲其他,敲過代碼,但也可能會遺忘,權當加深印象了;
5-1 大理石在哪裏(UVa 10474)
很容易的題目,sort+lower_bound,不過自己對lower_bound還是用的很少,欸,所以還是不太敢用的= =;
#define _CRT_SECURE_NO_WARNINGS #include<iostream> #include<cstdio> #include<algorithm> using namespace std; const int maxn = 10005; int num[maxn]; int main() { int n, q, kase = 0; while (cin >> n >> q&&n) { printf("CASE# %d:\n", ++kase); for (int i = 0; i < n; i++) scanf("%d", &num[i]); sort(num, num + n); int temp; while(q--){ scanf("%d", &temp); int k = lower_bound(num, num + n, temp) - num; if (num[k] == temp&&k<n) printf("%d found at %d\n", temp, k + 1); else printf("%d not found\n", temp); } } return 0; }
5-2 木塊問題(UVa 101)
直接看劉老師的題意,還是有點懵逼的,不過再看劉老師給的代碼,就理解了題意,同時又驚嘆于劉老師的代碼,寫得如此優美,很多意想不到的東西;
嗯,這題忘記得差不多了,不過題目不難,看了題目,估計可以隨手寫;
#include<cstdio> #include<iostream> #include<vector> #include<string> using namespace std; const int maxn = 30; int n; vector<int> pile[maxn]; void find(int a, int& p, int& h) { for (p = 0; p < n; p++) for (h = 0; h < pile[p].size(); h++) if (pile[p][h] == a) return; } void clear(int p, int h) { for (size_t i = h + 1; i < pile[p].size(); i++) pile[pile[p][i]].push_back(pile[p][i]); pile[p].resize(h + 1); } void pile_onto(int p, int h, int p2) { for (size_t i = h; i < pile[p].size(); i++) pile[p2].push_back(pile[p][i]); pile[p].resize(h); } int main() { int a, b; cin >> n; string s1, s2; for (int i = 0; i < n; i++) pile[i].push_back(i); while (cin >> s1 >> a >> s2 >> b) { if (s1 == "quit") break; int pa, pb, ha, hb; find(a, pa, ha); find(b, pb, hb); if (pa == pb) continue; if (s2 == "onto") clear(pb, hb); if (s1 == "move") clear(pa, ha); pile_onto(pa, ha, pb); } for (int i = 0; i < n; i++) { printf("%d:", i); for (size_t j = 0; j < pile[i].size(); j++) printf(" %d", pile[i][j]); putchar('\n'); } return 0; }
5-3 安迪的第一個字典 (UVa 10815)
這題很簡答,就是把輸入轉換一下格式,然後字符串流,直接扔進set就輸出了;
#include<iostream> #include<string> #include<cctype> #include<set> #include<sstream> using namespace std; set<string> dict; int main() { string s, buf; while (cin >> s) { for (int i = 0; i < s.size(); i++) if (isalpha(s[i])) s[i] = tolower(s[i]); else s[i] = ' '; stringstream ss(s); while (ss >> buf) dict.insert(buf); } for (set<string>::iterator it = dict.begin(); it != dict.end(); it++) cout << *it << endl; return 0; }
5-4反片語 (UVa 156)
額,這題轉換格式再sort;
#include<iostream> #include<algorithm> #include<map> #include<cctype> #include<vector> #include<string> using namespace std; vector<string> word; map<string, int> temp; string reper(string &s) { string t = s; for (int i = 0; i < s.size(); i++) t[i] = tolower(s[i]); sort(t.begin(), t.end()); return t; } int main() { string s; while (cin >> s) { if (s[0] == '#') break; word.push_back(s); string t = reper(s); if (!temp.count(t)) temp[t] = 0; temp[t]++; } vector<string> ans; for (vector<string>::iterator it = word.begin(); it != word.end(); it++) if (temp[reper(*it)] == 1) ans.push_back(*it); sort(ans.begin(), ans.end()); for (int i = 0; i < ans.size(); i++) cout << ans[i] << endl; return 0; }
5-5集合棧計算機(UVa 12096)
嗯,這題有點坑啊,讀不太懂劉老師描述的題意,是看了代碼和樣例才搞懂的,總的來説也不難= =;
#include<iostream> #include<stack> #include<vector> #include<set> #include<string> #include<map> #include<algorithm> #include<iterator> using namespace std; typedef set<int> Set; map<Set, int> idcache; vector<Set> setcache; int id(Set x) { if (idcache.count(x)) return idcache[x]; setcache.push_back(x); return idcache[x] = setcache.size() - 1; } #define ALL(x) x.begin(),x.end() #define INS(x) inserter(x,x.begin()) int main() { int t; cin >> t; while (t--) { stack<int> s; int n; cin >> n; for (int i = 0; i < n; i++) { string op; cin >> op; if (op[0] == 'P') s.push(id(Set())); else if (op[0] == 'D') s.push(s.top()); else { Set x1 = setcache[s.top()]; s.pop(); Set x2 = setcache[s.top()]; s.pop(); Set x; if (op[0] == 'U') set_union(ALL(x1), ALL(x2), INS(x)); if (op[0] == 'I') set_intersection(ALL(x1), ALL(x2), INS(x)); if (op[0] == 'A') { x = x2; x.insert(id(x1)); } s.push(id(x)); } cout << setcache[s.top()].size() << endl; } cout << "***\n"; } return 0; }
5-6團體隊列(UVa 540)
嗯,用隊列去模擬優先隊列,也不難;
#define _CRT_SECURE_NO_WARNINGS #include<iostream> #include<map> #include<queue> #include<cstdio> using namespace std; const int maxn = 1e3 + 10; int main() { int t, kase=0; while (cin >> t&&t) { printf("Scenario #%d\n", ++kase); map<int, int> team; int n, x; for (int i = 0; i < t; i++) { cin >> n; while (n--) { scanf("%d", &x); team[x] = i; } } queue<int> q, q2[maxn]; for (;;) { char cmd[10]; scanf("%s", cmd); if (cmd[0] == 'S') break; else if (cmd[0] == 'D') { int t = q.front(); printf("%d\n", q2[t].front()); q2[t].pop(); if (q2[t].empty()) q.pop(); } else if (cmd[0] == 'E') { scanf("%d", &x); if (q2[team[x]].empty()) q.push(team[x]); q2[team[x]].push(x); } } printf("\n"); } return 0; }
5-7丑數(UVa 136)
不難,代碼貌似有點玄,不過還好,想一下就清楚了;
#include<iostream> #include<map> #include<vector> #include<queue> #include<set> #include <functional> using namespace std; typedef long long ll; const int temp[3] = { 2,3,5 }; int main() { priority_queue<ll, vector<ll>, greater<ll> > pq; set<ll> s; pq.push(1); s.insert(1); for (int i = 1;; i++) { ll x = pq.top(); pq.pop(); if (i == 1500) { cout << "The 1500'th ugly number is " << x << ".\n"; break; } for (int j = 0; j < 3; j++) { ll x2 = x*temp[j]; if (!s.count(x2)) { s.insert(x2); pq.push(x2); } } } return 0; }
5-8 Unix Is命令 (UVa 400)
嗯哼,貌似當初寫這題,折騰好久的呢,控制輸出的時候的行列那些= =額,貌似忘了
#define _CRT_SECURE_NO_WARNINGS #include<iostream> #include<cstdio> #include<string> #include<algorithm> using namespace std; const int maxcol = 60; const int maxn = 105; string failnames[maxn]; void print(const string&s, int len, char extra) { cout << s; for (int i = 0; i < len - s.length(); i++) cout << extra; } int main() { int n; while (cin>>n) { int M = 0; for (int i = 0; i < n; i++) { cin >> failnames[i]; M = max(M, (int)failnames[i].length()); } int cols = (maxcol - M) / (M + 2) + 1; int rows = (n - 1) / cols + 1; print("", maxcol, '-'); cout << endl; sort(failnames, failnames + n); for (int i = 0; i < rows; i++) { for (int j = 0; j < cols; j++) { int idx = j*rows + i; if (idx < n) print(failnames[idx], j == cols - 1 ? M : M + 2, ' '); } cout << endl; } } return 0; }
5-9 數據庫(UVa 1592)
額,這題不難的,不過曲解了劉老師的描述,貌似是看了劉老師的代碼,然後才寫出來的?當時的忘了是TLE了還是WA了= =欸,記性好差額
#define _CRT_SECURE_NO_WARNINGS #include<iostream> #include<cstdio> #include<vector> #include<map> #include<string> #include<utility> #include<cstring> using namespace std; const int M = 15; const int N = 10005; typedef pair<int, int> P; map<string,int> idcache; int cnt, n, m, db[N][M]; string getstr(char * s) { int c; while ((c = getchar()) == '\n' || c == ' ') ; s[0] = c; for (int i = 1; (c = getchar()) != ',' && c != '\n' && c != EOF; i++) s[i] = c; string str = s; return str; } int ID(const string &s) { if (!idcache.count(s)) idcache[s]=++cnt; return idcache[s]; } void find() { for (int i = 0; i < m; i++) for (int j = i + 1; j < m; j++) { map<P, int> ans; for (int k = 0; k < n; k++) { P p = make_pair(db[k][i], db[k][j]); if (ans.count(p)) { cout << "NO\n"; cout << ans[p] + 1 << " " << k+1 << endl; cout << i+1 << " " << j+1 << endl; return; } ans[p] = k; } } cout << "YES\n"; } int main() { while (cin >> n >> m) { char str[105]; idcache.clear(); cnt = 0; for (int i = 0; i < n; i++) for (int j = 0; j < m; j++) { memset(str, 0, sizeof(str)); db[i][j] = ID(getstr(str)); } find(); } return 0; }
5-10 PGA巡迴賽的獎金(UVa 207)
這題好麻煩啊= =,代碼貼在另一個隨筆了;
5-11 郵件傳輸代理的交互(UVa 814)
嗯,題意里有個東西還不是很清楚,不過貌似不影響AC,而且劉老師代碼裏面也沒體現
#include<iostream> #include<string> #include<set> #include<vector> #include<map> using namespace std; #define FOR(i, n) for (int i = 0; i < (n);i++) void get_add(const string& temp, string& user, string& mta) { int mid = temp.find('@'); user = temp.substr(0, mid); mta = temp.substr(mid + 1); } int main() { string temp, str, user1, user2, mta1, mta2; set<string> sstr; int n; while (cin >> temp&&temp != "*") { cin >> mta1 >> n; FOR(i, n) { cin >> temp; sstr.insert(temp + "@" + mta1); } } while (cin >> str&&str != "*") { get_add(str, user1, mta1); //cout << user1 << " " << mta1 << endl; vector<string> mta; map<string, vector<string> > dest; set<string> vis; while (cin >> temp&&temp != "*") { get_add(temp, user2, mta2); if (vis.count(temp)) continue; vis.insert(temp); if (!dest.count(mta2)) { mta.push_back(mta2); dest[mta2] = vector<string>(); } dest[mta2].push_back(temp); } getline(cin, temp); string data; while (getline(cin, temp) && temp[0] != '*') data += " " + temp + "\n"; FOR(i, mta.size()) { string mta2 = mta[i]; vector<string> users = dest[mta2]; cout << "Connection between " << mta1 << " and " << mta2 << endl; cout << " HELO " << mta1 << endl; cout << " 250\n"; cout << " MAIL FROM:<" << str << ">\n"; cout << " 250\n"; bool ok = false; FOR(i, users.size()) { cout << " RCPT TO:<" << users[i] << ">\n"; if (sstr.count(users[i])) { ok = true; cout << " 250\n"; } else cout << " 550\n"; } if (ok) { cout << " DATA\n 354\n"; cout << data; cout << " .\n"; cout << " 250\n"; } cout << " QUIT\n 221\n"; } } return 0; }
5-12城市正視圖(UVa 221)
嗯,第二次看第五章,之前直接把這個跳過的,後來才發現,其實很簡單而已= =就是把各個X坐標都存起來,然後各個X坐標分析一下能否見,然而自己被搞暈過,看到最後面的從前往後遍歷,忘記了sort了一下,位置已經不然讀入的時候的位置了;
#include<iostream> #include<algorithm> #include<cstdio> #include<set> using namespace std; const int maxn = 105; struct building { int id; double x, y, d, w, h; bool operator < (const building& rhs)const { return x < rhs.x || (x == rhs.x &&y < rhs.y); } } b[maxn]; int n; double x[maxn * 2]; bool cover(int i, double mx) { return b[i].x <= mx&&b[i].x + b[i].w >= mx; } bool visible(int i, double mx) { if (!cover(i, mx)) return false; for (int k = 0; k < n; k++) if (b[k].y<b[i].y&&b[k].h>=b[i].h&&cover(k, mx)) return false; return true; } int main() { int kase = 0; while (scanf("%d", &n) == 1 && n) { for (int i = 0; i < n; i++) { scanf("%lf%lf%lf%lf%lf", &b[i].x, &b[i].y, &b[i].w, &b[i].d, &b[i].h); x[i * 2] = b[i].x; x[i * 2 + 1] = b[i].x + b[i].w; b[i].id = i + 1; } sort(b, b + n); sort(x, x + 2 * n); int m = unique(x, x + n * 2) - x; if (kase++) printf("\n"); printf("For map #%d, the visible buildings are numbered as follows:\n%d", kase, b[0].id); for (int i = 1; i < n; i++) { bool vis = false; for (int j = 0; j < m - 1; j++) if (visible(i, (x[j] + x[j + 1]) / 2)) { vis = true; break; } if (vis) printf(" %d", b[i].id); } printf("\n"); } return 0; }