3708 Problem C 剪花布條
阿新 • • 發佈:2019-01-01
問題 C: 剪花布條
時間限制: 1000 Sec 記憶體限制: 10000 MB
提交: 33 解決: 17
題目描述
一塊花布條,裡面有些圖案,另有一塊直接可用的小飾條,裡面也有一些圖案。對於給定的花布條和小飾條,計算一下能從花布條中儘可能剪出幾塊小飾條來呢?
輸入
輸入中含有一些資料,分別是成對出現的花布條和小飾條,其布條都是用可見ASCII字元表示的,可見的ASCII字元有多少個,布條的花紋也有多少種花樣。花紋條和小飾條不會超過1000個字元長。如果遇見#字元,則不再進行工作。
輸出
輸出能從花紋布中剪出的最多小飾條個數,如果一塊都沒有,那就老老實實輸出0,每個結果之間應換行。
樣例輸入
abcde a3 aaaaaa aa #
樣例輸出
0 3
經驗總結
這題的KMP演算法注意一點,就是在匹配成功後,模式串的指標不是滑到上一個最大匹配的位置,而是直接重新匹配(即 j = - 1),其他的就沒什麼啦~~
正確程式碼
#include <cstdio> #include <algorithm> #include <cstring> #include <vector> #include <iostream> #include <string> using namespace std; const int maxn=1010; int nextval[maxn]; char c1[maxn],c2[maxn]; void getNextval(char str[]) { int j=-1; nextval[0]=-1; for(int i=1;i<strlen(str);++i) { while(j!=-1&&str[i]!=str[j+1]) { j=nextval[j]; } if(str[i]==str[j+1]) { ++j; } if(j==-1||str[i+1]!=str[j+1]) { nextval[i]=j; } else { nextval[i]=nextval[j]; } } } int KMP(char str1[],char str2[]) { int ans=0,j=-1; int n=strlen(str1),m=strlen(str2); for(int i=0;i<n;++i) { if(j!=-1&&str1[i]!=str2[j+1]) { j=nextval[j]; } if(str1[i]==str2[j+1]) { ++j; } if(j==m-1) { ans++; j=-1; } } return ans; } int main() { int ans; while(~scanf("%s",c1)) { if(strlen(c1)==1&&c1[0]=='#') break; scanf("%s",c2); getNextval(c2); ans=0; ans+=KMP(c1,c2); printf("%d\n",ans); } return 0; }