Question:
Give n characters in length and m words. Each word has a valid value.
Output weights and words with a length not greater than N
If the cost is the same, the output length is short, and the output Lexicographic Order with the same length is the smallest.
Ideas:
Open a string array to store words for each node!
Other ideas are the same as those of DP.
Note: If the sum is zero, an empty string is output.
Code:
#include"cstdlib"#include"cstdio"#include"cstring"#include"cmath"#include"queue"#include"algorithm"#include"iostream"using namespace std;int triecont;char fuck[55][1234][55];struct word{ char x[12]; int k;} w[123];struct trie{ int mark,id; trie *next[27],*fail; trie() { mark=id=0; memset(next,0,sizeof(next)); fail=NULL; }};trie *root,*node[2340];void init(char *v,int k){ trie *p=root; for(int i=0;v[i];i++) { int tep=v[i]-'a'; if(p->next[tep]==NULL) { p->next[tep]=new trie(); node[triecont]=p->next[tep]; p->next[tep]->id=triecont++; } p=p->next[tep]; } p->mark+=k;}void getac(){ queue<trie*>q; q.push(root); while(!q.empty()) { trie *p=q.front(); q.pop(); for(int i=0;i<26;i++) { if(p->next[i]==NULL) { if(p==root) p->next[i]=root; else p->next[i]=p->fail->next[i]; } else { if(p==root) p->next[i]->fail=root; else p->next[i]->fail=p->fail->next[i]; q.push(p->next[i]); if(p!=root) p->next[i]->mark+=p->next[i]->fail->mark; } } }}int cmp(char *a,char *b){ int len1=strlen(a); int len2=strlen(b); if(len1!=len2) { if(len1<len2) return 1; return 0; } else { if(strcmp(a,b)<0) return 1; return 0; }}int dp[55][1234];int main(){ int t; cin>>t; while(t--) { int n,m; scanf("%d%d",&n,&m); memset(node,0,sizeof(node)); triecont=0; root=new trie(); node[triecont]=root; root->id=triecont++; for(int i=0; i<m; i++) scanf("%s",w[i].x); for(int i=0; i<m; i++) scanf("%d",&w[i].k); for(int i=0; i<m; i++) { init(w[i].x,w[i].k); } getac(); memset(dp,-1,sizeof(dp)); dp[0][0]=0; char ans[55]; strcpy(fuck[0][0],""); strcpy(ans,""); int Max=0; for(int i=1;i<=n;i++) { for(int j=0;j<triecont;j++) { if(dp[i-1][j]==-1) continue; for(int k=0;k<26;k++) { trie *p=node[j]->next[k]; int sum=dp[i-1][j]+p->mark; char tep[55]; strcpy(tep,fuck[i-1][j]); int len=strlen(tep); tep[len]='a'+k; tep[len+1]='\0'; if(sum>dp[i][p->id] || (sum==dp[i][p->id] && cmp(tep,fuck[i][p->id]))) { dp[i][p->id]=sum; strcpy(fuck[i][p->id],tep); if(sum>Max || (sum==Max && cmp(tep,ans))) { Max=sum; strcpy(ans,tep); } } } } } puts(ans); } return 0;}
[AC + dp + record path] HDU 2825 Ring