NOI2011 阿狸的打字機

2021-08-14 08:07:14 字數 2016 閱讀 7862

阿狸喜歡收藏各種稀奇古怪的東西,最近他淘到一台老式的打字機。打字機上只有28個按鍵,分別印有 26個小寫英文本母和』b』、』p』兩個字母。 經阿狸研究發現,這個打字機是這樣工作的:

輸入小寫字母,打字機的乙個凹槽中會加入這個字母(按 p 前凹槽中至少有乙個字母)。

按一下印有』b』的按鍵,打字機凹槽中最後乙個字母會消失。

按一下印有』p』的按鍵,打字機會在紙上列印出凹槽中現有的所有字母並換行,但凹槽中的字母不會消失(保證凹槽中至少有乙個字母) 。

例如,阿狸輸入 apapbbp,紙上被列印的字元如下:

a aa

ab 我們把紙上列印出來的字串從 1開始順序編號,一直到 n。打字機有乙個非常有趣的功能,在打字機中暗藏乙個帶數字的小鍵盤,在小鍵盤上輸入兩個數(x,y)(其中1≤x,y≤n),打字機會顯示第x個列印的字串在第y個列印的字串中出現了多少次。 阿狸發現了這個功能以後很興奮,他想寫個程式完成同樣的功能,你能幫助他麼?

比較幾個匹配串,一般來說ac自動機是乙個很好的選擇。

根據輸入的第乙個長字串,考慮p和b表示什麼。

建造trie的時候,p表示標記,b表示回到自己的父親,小寫字母表示向下走。

但是有這麼多組詢問,怎麼用很短的時間解決掉他們呢?

題目條件:

①被列印的字串是有序的,即trie上的乙個節點表示被列印的字串的乙個區間[l,r]。

②問乙個串在另乙個串中出現了幾次。

相應對策:

那麼再跑一遍trie,就可以解決掉[l,r]區間的問題。

只需要在進來這個點時在資料結構中+1,出去時-1即可。

問次數,就是問在fail樹上,根節點到某個其子樹種節點的路徑上,有幾個+1。

#include

#include

#include

#include

#include

#include

#define n 100010

#define p(a) putchar(a)

#define fo(i,a,b) for(i=a;i<=b;i++)

using

namespace

std;

struct note;note qu[n];

struct note1;note1 edge[n];

int tot,head[n],ans[n];

int i,j,k,l,n,m,x,gs,cs,wz,y;

int c[n],u,v;

int tr[n][26],fail[n],bz[n],pre[n];

int dfn[n],t,fa[n];

int val[n],siz[n];

char s[n],ch;

queue

q;int read()

void write(int x)

void lb(int x,int y)

int lowbit(int x)

void ins(int x,int delta)

int query(int x)

void dfs(int x)

}bool cmp(note x,note y)

k=0;gs=0;pre[0]=-1;

fo(i,1,l)

} else

if(ch=='b')k=pre[k];else bz[++cs]=k;

}fail[0]=-1;

q.push(0);

while(!q.empty())

}fo(i,1,gs)lb(fail[i],i);

dfs(0);

sort(qu+1,qu+n+1,cmp);

k=0;y=1;

ins(1,1);

fo(i,1,l) else

if(ch=='b')

else}}

ins(1,-1);

fo(i,1,n)write(ans[i]),p('\n');

return

0;}

NOI2011阿狸的打字機

阿狸喜歡收藏各種稀奇古怪的東西,最近他淘到一台老式的打字機。打字機上只有28個按鍵,分別印有26個小寫英文本母和 b p 兩個字母。經阿狸研究發現,這個打字機是這樣工作的 l 輸入小寫字母,打字機的乙個凹槽中會加入這個字母 這個字母加在凹槽的最後 l 按一下印有 b 的按鍵,打字機凹槽中最後乙個字母...

NOI2011阿狸的打字機

剛學完字串演算法做一做題,這道題的質量的確很高,做完以後感覺對ac自動機有長進 一下的神仙思路來自yyb dalao 蒟蒻開始只想到了40分暴力,全程靠題解 step1 首先直接處理出所有的串再裸kmp好寫,但是覺得得分應該不高,也沒有人說能拿多少分 這個題正解的第一步是要想到ac自動機,準確地說和...

NOI2011 阿狸的打字機

調了下午到晚上 從0 40 70 100 心力交瘁 40分做法 直接在fail樹上暴力跳,修改節點值,樹狀陣列查詢時間複雜度n 2log 70分做法 接近正解,離線詢問,在對應的位置打標記,dfs的時候可以遍歷到這個點的時候,對這個點所有的詢問都可以同時處理出來 100分做法 讀入的時侯可以優化一下...