hdu1298(字典樹)
阿新 • • 發佈:2018-08-02
eno aps class 按鍵 -a pen 代碼 lan max
T9
題意:
給出每個單詞的權值,現在使用九鍵拼音,根據用戶的按鍵彈出權值最大單詞,如果答案有多個,彈出字典序最小的,問當用戶按下一個鍵時,應該彈出哪個單詞。規定每次按鍵的值一定是1-9的數字,如果為1不用處理。對於一系列按鍵,如果字典中沒有與之對應的單詞,輸出“MANUALLY”。如果單詞a是單詞b的前綴,那麽a的權值為兩者的累加和,例如對於hel 2,hello 4,hel的權值為2+4=6。如果一個單詞在字典中,那麽它的前綴也可以認為是在字典中,並且對應的權值為該字母的權值。
分析:
首先根據給出的單詞建立一顆字典樹,根據題目意思,權值是可以累加的,並且一個單詞的前綴也是在字典中的,所以我們在插入一個單詞時,所經過的節點都需加上該單詞的權值。當我們進行按鍵的查詢時,用dfs枚舉出按鍵對應的所有的單詞,計算出每一個單詞在字典樹中的權值,取其中權值最大的單詞輸出即可。主要是註意一下細節的處理吧,註意不要隨便釋放節點的空間(Re在這裏好多次),按鍵為1的處理,在字典樹中找不到對應單詞的處理。
代碼:
#include <map> #include <queue> #include <math.h> #include <string> #include <stdio.h> #include <string.h> #include <iostream> #include <algorithm> using namespace std; #define ll long long #define ull unsigned long long #define cls(x) memset(x,0,sizeof(x)) #defineView Codeclslow(x) memset(x,-1,sizeof(x)) const int wordLen=200; const int maxn=1e5+100; int n,q,T,add; char s[wordLen],t[wordLen]; char mp[]={‘ ‘,‘ ‘,‘a‘,‘d‘,‘g‘,‘j‘,‘m‘,‘p‘,‘t‘,‘w‘}; struct TrieNode { int weight; TrieNode* nex[26]; }; TrieNode* root; struct Suffix { int maxw; char* str; }; Suffix suffix[wordLen]; TrieNode* build() { TrieNode* node=new TrieNode; node->weight=0; cls(node->nex); return node; } void Insert(char* s,int add) { int len=strlen(s); TrieNode* node=root; for(int i=0;i<len;i++){ int x=s[i]-‘a‘; if(node->nex[x]==NULL){ node->nex[x]=build(); } node=node->nex[x]; node->weight+=add; } } int Find(char* s) { int len=strlen(s); TrieNode* node=root; for(int i=0;i<len;i++){ int x=s[i]-‘a‘; if(node->nex[x]==NULL){ return 0; } node=node->nex[x]; } return node->weight; } void del(TrieNode* node) { for(int i=0;i<26;i++){ if(node->nex[i]!=NULL){ del(node->nex[i]); } } free(node); } void dfs(char* s,int pos) { if(s[pos]==‘1‘) return; int len=3; char ch=mp[s[pos]-‘0‘]; if(s[pos]==‘7‘||s[pos]==‘9‘) len=4; for(char i=ch;i<ch+len;i++){ t[pos]=i; t[pos+1]=‘\0‘; int reval=Find(t); if(reval==0) continue; // cout<<reval<<" "<<t<<endl; if(reval>suffix[pos].maxw){ suffix[pos].str=new char[strlen(t)]; strcpy(suffix[pos].str,t); suffix[pos].maxw=reval; } dfs(s,pos+1); } if(suffix[pos].maxw==0){ int slen=strlen(s); for(int i=pos;i<slen-1;i++){ suffix[i].maxw=0; suffix[i].str=new char[10]; strcpy(suffix[i].str,"MANUALLY"); } } } int main() { // freopen("in.txt","r",stdin); scanf("%d",&T); for(int kase=1;kase<=T;kase++){ printf("Scenario #%d:\n",kase); root=build(); scanf("%d",&n); for(int i=1;i<=n;i++){ scanf("%s%d",s,&add); Insert(s,add); } scanf("%d",&q); for(int i=1;i<=q;i++){ scanf("%s",s); dfs(s,0); int slen=strlen(s); for(int j=0;j<slen-1;j++){ printf("%s\n",suffix[j].str); suffix[j].maxw=0; } printf("\n"); } del(root); printf("\n"); } return 0; }
hdu1298(字典樹)