BJOI2018 二進位制

2022-06-20 14:15:07 字數 2366 閱讀 1003

題目鏈結

pupil 發現對於乙個十進位制數,無論怎麼將其的數字重新排列,均不影響其是不是 的倍數。他想研究對於二進位制,是否也有類似的性質。

於是他生成了乙個長為n 的二進位制串,希望你對於這個二進位制串的乙個子區間,能求出其有多少位置不同的連續子串,滿足在重新排列後(可包含前導0)是乙個3 的倍數。

兩個位置不同的子區間指開始位置不同或結束位置不同。

由於他想嘗試盡量多的情況,他有時會修改串中的乙個位置,並且會進行多次詢問。

首先,看到區間的子串,想到線段樹區間合併。

考慮乙個子問題:判斷乙個子串是否滿足條件。

首先,二進位制化為十進位制的方法是對應位×位權。

可以發現,位權\(mod3\)的值是\(1,2,1,2\)交替。

設這個子串有x個1放在2上,y個放在1上,則應滿足\((2x+y)mod3=0\),即\(x=y(mod3)\)。

設該子串長度為len,有s個1。

那麼,貪心的想,x和y相差0或3。

分情況討論:

\(len\%2=0\),\(s\%2=0\)。需要滿足\(s/2<=len/2\),顯然可以。

\(len\%2=0\),\(s\%2=1\)。即\(x+y=s,x-y=3\),解得\(x=(s+3)/2\)。需要滿足\((s+3)/2<=len/2\),即\(s<=len-3\)。

\(len\%2=1\),\(s\%2=0\)。需要滿足\(s/2<=(len-1)/2\),顯然可以。

\(len\%2=1\),\(s\%2=1\)。同理,\(x=(s+3)/2\)。需要滿足\((s+3)/2<=(len+1)/2\),即\(s<=len-2\)。

可以發現,s為偶數時一定可以。s為奇數時比較複雜,難以統計(因為即使len確定,滿足要求的s有很多,無法進行區間合併)。

考慮容斥,求不合法的。

若不合法,則\(s\%2=1\)。

分兩種情況討論:

\(len\%2=0\),即\(s>=len-2\)。因為\(s\%2=1,s<=len\),所以\(s=len-1\)。

\(len\%2=1\),即\(s>=len-1\)。因為\(s\%2=1,s<=len\),所以\(s=len\)。

此外,若\(s=1\),也不合法。把這部分減去,再加上\(s=1\)且\(len<=2\)的情況(被算了兩次)。

時間複雜度:\(o(mlogn)\),常數很大。

注意區間合併的細節。

#include #define ll long long 

struct sjd

};sjd operator * (sjd a, sjd b)

} return rt;

}sjd operator + (sjd a, sjd b)

sjd he[400010],zg[400010],zl[400010],zr[400010];

ll s0[400010],s1[400010],s2[400010];

bool h0[400010],h1[400010];

int sz[100010],l0[400010],l1[400010],r0[400010],r1[400010],su[400010],ma = 0,sl;

void fuz(int i, int j)

void merge(int i, int cl, int cr, int m)

void pushup(int i, int l, int r)

void getddz(int i, int x)

void jianshu(int i, int l, int r)

int m = (l + r) >> 1;

jianshu(i << 1, l, m);

jianshu((i << 1) | 1, m, r);

pushup(i, l, r);

}void xiugai(int i, int l, int r, int j)

int m = (l + r) >> 1;

if (j < m) xiugai(i << 1, l, m, j);

else xiugai((i << 1) | 1, m, r, j);

pushup(i, l, r);

}void getans(int i, int l, int r, int l, int r)

int m = (l + r) >> 1;

getans(i << 1, l, m, l, r);

getans((i << 1) | 1, m, r, l, r);

}ll getans(int n, int l, int r)

int main() else

} return 0;

}

BJOI2018 二進位制

題目鏈結 pupil 發現對於乙個十進位制數,無論怎麼將其的數字重新排列,均不影響其是不是 的倍數。他想研究對於二進位制,是否也有類似的性質。於是他生成了乙個長為n 的二進位制串,希望你對於這個二進位制串的乙個子區間,能求出其有多少位置不同的連續子串,滿足在重新排列後 可包含前導0 是乙個3 的倍數...

BJOI2018 二進位制

題目位址 前置知識 線段樹 給定乙個長度為 n 的 01 串,m 次操作 先來解決乙個子問題,什麼樣的序列重排是 3 的倍數?設 s 為序列上 1 的個數,序列長度為 len 將二進位制下每位下的權列列舉出來,分別是 1,2,4,8,16,32.換成 bmod 3 意義下的權 1,2,1,2,1,2...

bzoj 5294 Bjoi2018 二進位制

pupil 發現對於乙個十進位制數,無論怎麼將其的數字重新排列,均不影響其是不是333 的倍數。他想研究對於二進 制,是否也有類似的性質。於是他生成了乙個長為n 的二進位制串,希望你對於這個二進位制串的乙個子區間,能求出 其有多少位置不同的連續子串,滿足在重新排列後 可包含前導0 是乙個3 的倍數。...