题目大意:给你n个可用单词,和一段文字,每句用句号隔开。问这段文字的感动值为多少(每句话有多少个可用单词,感动值就是多少,一句话中一个可用单词出现多次只算一个。最终答案为每句的感动值总和)。
解题思路:我们先用Trie存可用单词,然后对于那段文字,我们逐字符读入。用一个set储存当前句出现过的可用单词,对一个单词,如果没出现过,就去Trie里匹配即可。记得句末清空set。
注意:题目说会出现数字,所以要判断一些,我就因为没考虑这个而RE了。
C++ Code:
#include<cstdio> #include<set> #include<string> using namespace std; set<string>t; char s[5500]; int n; struct node{ int exist; node* nxt[26]; node():exist(0){ for(int i=0;i<26;++i)nxt[i]=NULL; } }*d; void ins(char* s){ node* p=d; for(int i=0;s[i];++i){ int v=tolower(s[i])-'a'; if(p->nxt[v]==NULL)p->nxt[v]=new node; p=p->nxt[v]; } p->exist=1; } int query(char* s){ node* p=d; for(int i=0;s[i];++i){ int v=s[i]-'a'; if(v<0||v>25)return 0; p=p->nxt[v]; if(p==NULL)return 0; } if(p->exist)return 1; return 0; } int main(){ d=new node; scanf("%d",&n); while(n--){ scanf("%s",s); ins(s); } fgets(s,4,stdin); int len=0,ans=0; char c; while((c=getchar())!=EOF){ c=tolower(c); if(c=='.'){ s[len]=0; if(!t.count(s)) ans+=query(s); len=0; t.clear(); continue; } if(c==','||c==' '){ s[len]=0; if(!t.count(s)) ans+=query(s); t.insert(s); len=0; } else s[len++]=c; } printf("%d ",ans); return 0; }