超时代码送上:
// UVa 1597 //#define LOCAL #include <iostream> #include <sstream> #include <cctype> // for tolower() isalpha() #include <string> #include <algorithm> // for set_union() set_intersection() set_difference() #include <set> using namespace std; #define ALL(x) x.begin(), x.end() #define INS(x) inserter(x, x.begin()) const int Max = 1500+5; const int maxn = 100+5; struct Array { int passage; string str; set <string> Set; } lines[Max]; int N, M, cnt = -1, rem; int rempos[maxn]; // to remember passage position void To_standard(string & str) { for (int i = 0; i < str.size(); ++i) if (isalpha(str[i])) str[i] = tolower(str[i]); else str[i] = ' '; } void Search(string & str, set<int> & setA) { // for line for (int i = 0; i < cnt+1; ++i) if (lines[i].Set.count(str)) setA.insert(i); } void Search1(string & str, set<int> & setA) { // for passage for (int i = 0; i < cnt+1; ++i) if (lines[i].Set.count(str)) setA.insert(lines[i].passage); } void Print(set <int> & Set) { for (int i = 0; i < cnt+1; ++i) if (Set.count(i)) { if (lines[i].passage != rem) { if (rem) cout << "----------" << endl; rem = lines[i].passage; } cout << lines[i].str << endl; } if (!Set.size()) cout << "Sorry, I found nothing.\n"; } void Print1(set <int> & Set) { for (int i = 1; i < N+1; ++i) if (Set.count(i)) { if (i != rem) { if (rem) cout << "----------" << endl; rem = i; } for (int j = rempos[i-1]+1; j < rempos[i]+1; ++j) cout << lines[j].str << endl; } if (!Set.size()) cout << "Sorry, I found nothing.\n"; } void Print2(const string & str1, const string & str2, set <int> & Set) { for (int i = 1; i < N+1; ++i) if (Set.count(i)) { if (i != rem) { if (rem) cout << "----------" << endl; rem = i; } for (int j = rempos[i-1]+1; j < rempos[i]+1; ++j) if (lines[j].Set.count(str1) || lines[j].Set.count(str2)) cout << lines[j].str << endl; } if (!Set.size()) cout << "Sorry, I found nothing.\n"; } int main() { #ifdef LOCAL freopen("test.in.txt", "r", stdin); freopen("test.out.txt", "w", stdout); #endif string line; cin >> N; cin.get(); for (int i = 0; i < N; ++i) { while (getline(cin, line) && line != "**********") { string temp; lines[++cnt].str = line; lines[cnt].passage = i+1; To_standard(line); stringstream ss(line); while (ss >> temp) lines[cnt].Set.insert(temp); } rempos[i+1] = cnt; } rempos[0] = -1; set <int> setD; // all passage for (int i = 0; i < N; ++i) setD.insert(i+1); cin >> M; cin.get(); for (int i = 0; i < M; ++i) { int count = -1; rem = 0; string str[3]; set <int> setA, setB, setC; getline(cin, line); To_standard(line); stringstream ss(line); while (ss >> str[++count]) {} --count; if (count == 0) { Search(str[0], setA); Print(setA); } if (count == 1) { Search1(str[1], setA); set_difference(ALL(setD), ALL(setA), INS(setC)); Print1(setC); } if (count == 2) if (str[1] == "and") { Search1(str[0], setA); Search1(str[2], setB); set_intersection(ALL(setA), ALL(setB), INS(setC)); Print2(str[0], str[2], setC); } else { Search(str[0], setA); Search(str[2], setB); set_union(ALL(setA), ALL(setB), INS(setC)); Print(setC); } cout << "==========" << endl; } return 0; }