日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Prefix HDU - 5790 字典树 + 主席树

發布時間:2023/12/4 编程问答 30 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Prefix HDU - 5790 字典树 + 主席树 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

傳送門

文章目錄

  • 題意:
  • 思路:

題意:

給你nnn個串,每次詢問一個區間,返回這個區間的串的不同的前綴個數,強制在線。

思路:

碰到字符串前綴的問題,我們自然的想到用字典樹來解決。
對于每個串,我們將其插入字典樹的時候記一下當前串的每個前綴的ididid,我們可以將問題就轉化成詢問區間內出現數字的個數(即出現的ididid),因為要強制在線,我們考慮用主席樹維護歷史信息。
對于維護區間內出現數字的個數,這是個經典問題了,維護前綴出現的最后一個位置即可。查詢的時候直接查詢第rrr棵樹的區間和即可。

//#pragma GCC optimize(2) #include<cstdio> #include<iostream> #include<string> #include<cstring> #include<map> #include<cmath> #include<cctype> #include<vector> #include<set> #include<queue> #include<algorithm> #include<sstream> #include<ctime> #include<cstdlib> #define X first #define Y second #define L (u<<1) #define R (u<<1|1) #define pb push_back #define mk make_pair #define Mid (tr[u].l+tr[u].r>>1) #define Len(u) (tr[u].r-tr[u].l+1) #define random(a,b) ((a)+rand()%((b)-(a)+1)) #define db puts("---") using namespace std;//void rd_cre() { freopen("d://dp//data.txt","w",stdout); srand(time(NULL)); } //void rd_ac() { freopen("d://dp//data.txt","r",stdin); freopen("d://dp//AC.txt","w",stdout); } //void rd_wa() { freopen("d://dp//data.txt","r",stdin); freopen("d://dp//WA.txt","w",stdout); }typedef long long LL; typedef unsigned long long ULL; typedef pair<int,int> PII;const int N=200110,mod=1e9+7,INF=0x3f3f3f3f; const int P=131; const double eps=1e-6;int n,m; int root[N],tot; int idx,num[N*5],tree[N][26],id,st[N*5]; int pre[N*5]; char s[N]; struct Node {int l,r;int cnt; }tr[N*40];int newnode() {idx++;for(int i=0;i<26;i++) tree[idx][i]=0;num[idx]=0;return idx; }void add() {int p=0;for(int i=0;s[i];i++){int now=s[i]-'a';if(!tree[p][now]) tree[p][now]=newnode();p=tree[p][now];if(!num[p]) num[p]=++id;st[i]=num[p];} }void insert(int p,int &q,int l,int r,int pos,int x) {q=++tot; tr[q]=tr[p];tr[q].cnt+=x;if(l==r) return;int mid=l+r>>1;if(pos<=mid) insert(tr[p].l,tr[q].l,l,mid,pos,x);else insert(tr[p].r,tr[q].r,mid+1,r,pos,x); }int query(int u,int l,int r,int ql,int qr) {if(!u) return 0;if(l>=ql&&r<=qr) return tr[u].cnt;int ans=0,mid=l+r>>1;if(ql<=mid) ans+=query(tr[u].l,l,mid,ql,qr);if(qr>mid) ans+=query(tr[u].r,mid+1,r,ql,qr);return ans; }int main() { // ios::sync_with_stdio(false); // cin.tie(0);memset(pre,-1,sizeof(pre));while(scanf("%d",&n)!=EOF){memset(tree,0,sizeof(tree));idx=tot=id=0;for(int i=1;i<=n;i++){scanf("%s",s);add();root[i]=root[i-1];for(int j=0;s[j];j++){if(pre[st[j]]==-1) insert(root[i],root[i],1,n,i,1);else{insert(root[i],root[i],1,n,pre[st[j]],-1);insert(root[i],root[i],1,n,i,1);}pre[st[j]]=i;}}scanf("%d",&m);int ans=0;while(m--){int ll,rr; scanf("%d%d",&ll,&rr);int l=min((ll+ans)%n,(rr+ans)%n)+1;int r=max((ll+ans)%n,(rr+ans)%n)+1;printf("%d\n",ans=query(root[r],1,n,l,r));}for(int i=1;i<=id;i++) pre[i]=-1;}return 0; } /**/

總結

以上是生活随笔為你收集整理的Prefix HDU - 5790 字典树 + 主席树的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。