51nod1532 帶可選字元的多字串匹配

2022-03-30 12:42:33 字數 1371 閱讀 3652

有乙個文字串,它的長度為m (1 <= m <= 2000000),現在想找出其中所有的符合特定模式的子串位置。

符合特定模式是指,該子串的長度為n (1 <= n <= 500),並且第i個字元需要在給定的字元集合si中。

因此,描述這一特定模式,共需要s1,s2,...,sn這n個字元集合。每個集合的大小都在1~62之間,其中的字元只為數字或大小寫字母。

input

第一行為乙個字串,表示待匹配的文字串。注意文字串中可能含有數字和大小寫字母之外的字元。

第二行為乙個整數n。

以下n行,分別描述n個字元集合。每行開始是乙個1~62之間的整數,隨後有乙個空格,接下來有乙個字串表示對應字元集合的內容。整數表示字元集合的大小,因此它也就是字串的長度。輸入保證字串中的字元只為數字或大小寫字母且沒有重複。

output

每當從某個位置開頭的,長度為n的子串符合輸入的模式,就輸出一行,其中包含乙個整數,為它在文字串的起始位置。位置編號從1開始。

如果文字串沒有任何位置符合輸入模式,則最後輸出乙個字串"null",佔一行。

就是問b串在a串裡出現的所有位置。和一般字串匹配的區別是每個字元可以匹配若干個字元。

shift_and演算法。

bool陣列can[i][j]==true表示a[i-j+1..i]能與b[1..j]匹配,match[ch][i]表示字元ch在不在b串第i個位置的集合裡。

can[i][j]=can[i-1][j-1]&map[a[i]][j]

這玩意可以用bitset加速。。時間複雜度o(m*n/64),

1 #include2 #include3 #include4 #include5

using

namespace

std;

6const

int maxn=505;7

int id[233

];8 bitsetcan[233

],now;

9char s[2002333

];10

inti,j,k,n,m;

1112

13int ra,fh;char

rx;14 inline int

read()

2021

char ss[10];int

len;

22 inline void outx(int

x)24

while(x)ss[++len]=x%10+48,x/=10;25

while(len)putchar(ss[len--]);26}

27int

main()

42if(!flag)puts("

null");

43 }

view code

hdu 5716 帶可選字元的多字串匹配

給你乙個原串 乙個匹配串 特殊的是,這個匹配串的每一位可能可以匹配不同的字母 問你可以匹配的位置 今天早上做51nod模糊搜尋的時候看到了ta ngjz t an gj z的乙個黑科技 於是去學了一下 像這種奇怪的匹配方法是不可以用kmp解決的 但是可以用一種壓位的方法做到nm 64 nm64 具體...

51NOD 1127 最短的包含字串

傳送門 給出乙個字串,求該字串的乙個子串s,s包含a z中的全部字母,並且s是所有符合條件的子串中最短的,輸出s的長度。如果給出的字串中並不包括a z中的全部字母,則輸出no solution。input 第1行,1個字串。字串的長度 100000。output 輸出包含a z的最短子串長度。如果沒...

51nod1127 最短的包含字串

給出乙個字串,求該字串的乙個子串s,s包含a z中的全部字母,並且s是所有符合條件的子串中最短的,輸出s的長度。如果給出的字串中並不包括a z中的全部字母,則輸出no solution。收起第1行,1個字串。字串的長度 100000。輸出包含a z的最短子串s的長度。如果沒有符合條件的子串,則輸出n...