UVa 1597 - Searching the Web

来源:互联网 发布:手机屏幕软件 编辑:程序博客网 时间:2024/06/05 01:56

这道题仍然是做了3个月,一直超时和WA,最后参考某大神的AC代码终于过了。巧妙的地方就是运用||和&&来进行搜索时的“和”和“或”操作,另外分析文章后的存储数据的数据结构也很重要,还有代码中很多重复的地方不妨#define了,可以使代码更加简洁。不过最后AC还是用了1.1秒,貌似有用字典树做的方法会更快吧。

#include <bits/stdc++.h>using namespace std;using State = bool[1505];#define FOR for (int j = limit[i]; j < limit[i + 1]; ++j)map<string, State> Index;vector<string> doc;int limit[128];void insert(string s, const int no){doc.push_back(s);for (auto & i : s){if (isalpha(i)) i = tolower(i);else i = ' ';}stringstream ss(s); string word;while (ss >> word)Index[word][no] = true;}int main(){ios::sync_with_stdio(false);int N, cnt = 0; cin >> N; cin.get();for (int n = 0; n < N; ++n) {string line;while (getline(cin, line)){if (line == "**********"){limit[n + 1] = cnt;break;}else insert(line, cnt++);}}int M; cin >> M; cin.get();while (M--){string cmd; getline(cin, cmd);bool *A, *B;State out = {0};if (cmd[0] == 'N'){A = Index[cmd.substr(4)];for (int i = 0; i < N; ++i){bool flag = true;FOR if (A[j]) { flag = false; break; }FOR out[j] = flag;}}else if (cmd.find("AND") != string::npos){A = Index[cmd.substr(0, cmd.find(" AND "))];B = Index[cmd.substr(cmd.find(" AND ")+5)];for (int i = 0; i < N; ++i){bool flagA = false, flagB = false;FOR if (A[j]) { flagA = true; break; }FOR if (B[j]) { flagB = true; break; }if (flagA && flagB) FOR out[j] = A[j] || B[j];}}else if (cmd.find("OR") != string::npos){A = Index[cmd.substr(0, cmd.find(" OR "))];B = Index[cmd.substr(cmd.find(" OR ") + 4)];for (int i = 0; i < cnt; ++i) out[i] = A[i] || B[i];}else memcpy(out, Index[cmd], sizeof(State));bool has_out = false;for (int i = 0; i < N; ++i){bool need_out = false;FOR if (out[j]) {need_out = true; break;}if (need_out){if (has_out) cout << "----------" << endl;FOR if (out[j]) cout << doc[j] << endl;has_out = true;}}if (!has_out) cout << "Sorry, I found nothing." << endl;cout << "==========" << endl;}return 0;}


0 0