NOI2015 品酒大會 SAM

2021-09-25 06:35:13 字數 3056 閱讀 7496

給定乙個母串s

ss題意:對於長度為len

lenle

n的子串集合aia_

ai​,

求a ia_

ai​中相同字串(不同位置)之間的組合方案之和,和aia_

ai​ 中 任意兩字串權值乘積的最大值

一子串權值為該子串最左端字元對應的權值(可能為負數)。

求出每一子串出現總數cnt

cntcn

t,d[i]

d[i]

d[i]

表示長度為i

ii的情況之和,

d [i

]+=c

nt∗(

cnt−

1)/2

d[i]+=cnt*(cnt-1)/2

d[i]+=

cnt∗

(cnt

−1)/

2;反向建出sam,同一節點裡的權值相同,維護最大,次大,最小,次小,上傳到父親,

用線段樹區間更新 len

[fa[

i]]+

1len[fa[i]]+1

len[fa

[i]]

+1——l en

[i

]len[i]

len[i]

區間的答案

update 2019.08.07:

好像不用線段樹用差分就可以。。。留給讀者自己思考吧(這個不難想)

#include

#define pf printf

#define sf scanf

#define re register

using

namespace std;

#define cs const

#define ll long long

#define lc (p<<1)

#define rc ((p<<1)|1)

cs int n=

6e5+10;

cs ll inf=

1e18

;ll dlt[n]

,cnt[n]

;int vl[n]

,len[n]

,fa[n]

,ch[n][30

],tot,las,n,d[n]

,g[n]

;ll num[n<<1]

,mx[n]

,dmx[n]

,mn[n]

,dmn[n]

;inline

void

build

(int p,

int l,

int r)

inline

void

update

(int p,

int l,

int r,

int ql,

int qr,ll v)

int mid=

(l+r)

>>1;

;if(qr<=mid)

update

(lc,l,mid,ql,qr,v)

;else

if(ql>mid)

update

(rc,mid+

1,r,ql,qr,v)

;else

update

(lc,l,mid,ql,qr,v)

,update

(rc,mid+

1,r,ql,qr,v);}

struct node

;inline

void

bfs())

;while

(!q.

empty()

)int mid=

(t.l+t.r)

>>1;

q.push

((node));

q.push

((node));

}}inline

void

init()

inline

void

add(

int c)

if(len[p]+1

==len[q]

)int clo=

++tot;

fa[clo]

=fa[q]

;fa[q]

=fa[cur]

=clo;

len[clo]

=len[p]+1

;memcpy

(ch[clo]

,ch[q]

,sizeof ch[clo]);

for(

;p&&ch[p]

[c]==q;p=fa[p]

)ch[p]

[c]=clo;

}inline

void

get(

)else

if(mn[fa[g[i]]]

else

if(dmx[g[i]]!=

-inf)

update(1

,1,n,len[fa[g[i]]]

+1,len[g[i]],

max(mx[g[i]

]*dmx[g[i]

],mn[g[i]

]*dmn[g[i]])

);}bfs()

;for

(int re i=

1;i<=n-1;

++i)

}char s[n]

;ll lmx=

-inf,ldmx=

-inf,lmn=inf,ldmn=inf;

signed main (

)for

(int re i=n;i>=1;

--i)

add(s[i]

-'a');

printf

("%lld %lld\n"

,1ll

*n*(n-1)

/2,max

(lmx*ldmx,ldmn*lmn));

get();

return0;

}

Noi 2015 品酒大會

題目等價於求任意兩對字尾的lcp的值小於等於1,2 n的個數,以及權值乘積的最大值。求出字尾陣列的height值,然後預處理出每個height值能夠成為最小的區間。考慮每個height的值對答案的貢獻 如果height i 能夠成為最小的區間為 l,r 那麼個數便是 l i 1 r i 1 而乘積最...

NOI2015 品酒大會

字尾自動機 首先考慮第一問 我們先將字尾自動機建出來,考慮每個節點,它出現的次數肯定是endpos的size 我們記為num 那麼選取這個節點的串的方案數即為c num,2 num num 1 2,所能貢獻的長度區間為這個節點對應的所有串的長度即 len fa x 1 len x 1 這裡可以差分一...

NOI2015 品酒大會

一年一度的 幻影閣夏日品酒大會 隆重開幕了。大會包含品嚐和趣味挑戰 兩個環節,分別向優勝者頒發 首席品酒家 和 首席獵手 兩個獎項,吸引了眾多品酒師參加。在大會的晚餐上,調酒師 rainbow 調製了 n 杯雞尾酒。這 n 杯雞尾酒排成一行,其中第 n 杯酒 1 i n 被貼上了乙個標籤si,每個標...