BZOJ4199 [Noi2015]品酒大會__BZOJ

來源:互聯網
上載者:User

建一個尾碼樹,dfs一遍維護子樹裡有多少個尾碼,子數內最大次大最小次小,用siz[x]*(siz[x]-1)/2可以更新mx[fa[x]]+1~mx[x]這段的選法,用max(mx1[x]*mx2[x],mn1[x]*mn2[x])可以更新mx[fa[x]]+1~mx[x]這段的最大值,拿個線段樹維護一下,然後爬一遍線段樹就可以了

感覺自從學會了尾碼數組半個月之後學會了尾碼自動機就再也沒打過尾碼數組-_-

#include<iostream>#include<cstdlib>#include<cstdio>#include<cstring>#include<cmath>#include<ctime>#include<algorithm>#include<iomanip>#include<vector>#include<stack>#include<queue>#include<map>#include<set>#include<bitset>using namespace std;#define MAXN 600010#define MAXM 1010#define ll long long#define INF 2000000000#define MOD 1000000007#define eps 1e-8struct vec{int to;int fro;};vec mp[MAXN];int tai[MAXN],cnt;int fa[MAXN],son[MAXN][26],mx[MAXN];int lst,rt,tot;int n;char s[MAXN];int P[MAXN];int a[MAXN];ll v1[MAXN<<1],v2[MAXN<<1];int siz[MAXN],MX[MAXN][5],MN[MAXN][5];inline void be(int x,int y){mp[++cnt].to=y;mp[cnt].fro=tai[x];tai[x]=cnt;}void ins(int x){int np=++tot,p=lst;mx[np]=mx[p]+1;while(p&&!son[p][x]){son[p][x]=np;p=fa[p];}if(!p){fa[np]=rt;}else{int q=son[p][x];if(mx[q]==mx[p]+1){fa[np]=q;}else{int nq=++tot;mx[nq]=mx[p]+1;memcpy(son[nq],son[q],sizeof(son[q]));fa[nq]=fa[q];fa[np]=fa[q]=nq;while(p&&son[p][x]==q){son[p][x]=nq;p=fa[p];}}}lst=np;}void add(int x,int y,int z,int l,int r,ll av){if(y==l&&z==r){v1[x]+=av;return ;}int mid=y+z>>1;if(r<=mid){add(x<<1,y,mid,l,r,av);}else if(l>mid){add(x<<1|1,mid+1,z,l,r,av);}else{add(x<<1,y,mid,l,mid,av);add(x<<1|1,mid+1,z,mid+1,r,av);}}void change(int x,int y,int z,int l,int r,ll cv){if(y==l&&z==r){v2[x]=max(v2[x],cv);return ;}int mid=y+z>>1;if(r<=mid){change(x<<1,y,mid,l,r,cv);}else if(l>mid){change(x<<1|1,mid+1,z,l,r,cv);}else{change(x<<1,y,mid,l,mid,cv);change(x<<1|1,mid+1,z,mid+1,r,cv);}}void dfs(int x){int i,y;ll t=0;for(i=tai[x];i;i=mp[i].fro){y=mp[i].to;dfs(y);siz[x]+=siz[y];MX[x][0]=MX[y][3];MX[x][1]=MX[y][2];MN[x][2]=MN[y][0];MN[x][3]=MN[y][1];sort(MX[x],MX[x]+4);sort(MN[x],MN[x]+4);}t=(ll)siz[x]*(siz[x]-1)/2;int l=mx[fa[x]]+1,r=min(mx[x],n-1);if(siz[x]>=2){add(1,0,n-1,l,r,t);change(1,0,n-1,l,r,max((ll)MX[x][3]*MX[x][2],(ll)MN[x][0]*MN[x][1]));}}void walk(int x,int y,int z,ll ans1,ll ans2){ans1+=v1[x];ans2=max(ans2,v2[x]);if(y==z){if(ans1){printf("%lld %lld\n",ans1,ans2);}else{printf("0 0\n");}return ;}int mid=y+z>>1;walk(x<<1,y,mid,ans1,ans2);walk(x<<1|1,mid+1,z,ans1,ans2);}int main(){lst=rt=tot=1;int i;scanf("%d",&n);scanf("%s",s+1);int p=rt;for(i=n;i;i--){ins(s[i]-'a');siz[P[i]=p=son[p][s[i]-'a']]++;}for(i=1;i<=tot;i++){MX[i][0]=MX[i][1]=MX[i][2]=MX[i][3]=-INF;MN[i][0]=MN[i][1]=MN[i][2]=MN[i][3]=INF;}for(i=1;i<=n;i++){scanf("%d",&MX[P[i]][3]);MN[P[i]][0]=MX[P[i]][3];}for(i=2;i<=tot;i++){be(fa[i],i);}mx[0]=-1;for(i=1;i<=n*4;i++){v2[i]=-((ll)INF*INF);}dfs(1);walk(1,0,n-1,0,-((ll)INF*INF));return 0;}/**/


聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.