題解:求解每個位置向左向右aa串的個數f[x],g[x];
列舉a的長度,每a個位置設乙個關鍵點
每乙個a一定僅且跨越乙個關鍵點
然後求出相鄰關鍵點向前向後的最長公共字首的長度,這會對一段區間的f,g產生影響;
用差分+字首和統計答案
#include#include#include#includeusing namespace std;const int maxn=40009;
int t;
int n;
struct suffix_array
for(int i=1;i<=m;++i)c[i]=0;
for(int i=1;i<=n;++i)c[x[y[i]]]++;
for(int i=2;i<=m;++i)c[i]+=c[i-1];
for(int i=n;i>=1;--i)sa[c[x[y[i]]]--]=y[i];
swap(x,y);
x[sa[1]]=p=1;
for(int i=2;i<=n;++i)
if(p>=n)break;
m=p;
} }int rank[maxn];
int height[maxn];
void getheight() }
int f[maxn][20];
void stinit()
void sainit()
}a[2];
int tb[2][maxn];
int main()
}// for(int i=1;i<=n;++i)printf("%d ",tb[0][i]);
// cout/ for(int i=1;i<=n;++i)printf("%d ",tb[1][i]);
// cout
long long ans=0;
for(int i=1;iprintf("%lld\n",ans);
} return 0;
}
bzoj 4650 Noi2016 優秀的拆分
原來只會兩個log平衡樹合併。後來圍觀claris在uoj群上秒題後會了這道題。列舉a b 的長度l,然後列舉i kl,考慮字首i,i l和字尾i 1,i l 1,求出字首的lcp和字尾的lcp,然後合法的方案就在乙個方案內。差分一下即可。注意要避免重複。ac 如下 include include ...
BZOJ4650 Noi2016 優秀的拆分
設 f i 表示以 i 結尾的square個數,g i 表示以 i 開頭的square個數,則 ans sum f ig 列舉square中長度的一半 l 每 l 步取乙個關鍵點,那麼每個該長度的square的肯定恰好經過兩個相鄰的關鍵點,且位置差距為 l 的字元一一匹配。所以相鄰關鍵點之間通過字尾...
BZOJ4560 NOI2016 優秀的拆分
bzoj 洛谷考慮乙個形如 aabb 的串是由兩個形如 aa 的串拼起來的 那麼我們設 f i 以位置 i 為結尾的形如 aa 串的個數 g i 以位置 i 為開頭的形如 aa 串的個數 therefore ans sum nf i g i 1 題目的難點轉化為求 f,g 但是,其實我們只要 o n...