Codeforces Global Round 2

這場題目設置有點問題啊,難度:Div.2 A->Div.2 B->Div.2 D->Div.2 C->Div.2 D->Div.1 D-> Div.1 E->Div.1 F簡直有毒數組

只AC 4題彷佛就是1000+名了spa

這種考驗手速的時刻Itst就比較擅長了,而後就紅名+拿衣服了……code

A. Ilya and a Colorful Walk

若是最左邊和最右邊不一樣就是$N-1$,不然就是中間跟兩邊顏色不一樣的塊到兩邊距離的最大值排序

代碼ip

B. Alyona and a Narrow Fridge

二分答案,對於一個二分值$mid$將全部要放的牛奶拿出來,每一次最高的和次高的放在一層get

代碼it

C. Ramesses and Corner Inversion

注意到對任意$x \times y$的矩形作一次操做,等價於對這個矩形內全部$2 \times 2$的子矩形作一次操做,因而咱們只須要對$2 \times 2$的矩形作操做就能夠了,這個直接從左往右、從上往下、要翻轉就翻轉就能夠了io

代碼test

D. Frets On Fire

題目至關於要求:有$n$條線段,左端點爲$s_i$;$q$組詢問,每一組詢問每條線段的長度都爲$l$,問線段覆蓋總長度date

設$s_{i+1} = INF$,那麼答案就是$\sum\limits_{i=1}^n \min{s_{i+1} - s_i , l}$。把全部$s_{i+1}-s_i$存下來排個序,每一次詢問時二分

代碼

E. Pavel and Triangles

顯然每一次選出的三角形的邊長必定是$(2^i,2^i,2^j)$,其中$j \leq i$。因此能夠從小往大貪心,每一次選擇儘量多的三角形,即先把$< i$的剩下的木棒儘量地用掉,而後再3個3個地取當前剩餘的木棒

代碼

F. Niyaz and Small Degrees

先考慮對於一個$x$求答案。考慮樹形DP。

設$val_u$表示$u$到它父親的邊的權值,設$f_{u , flag = 0/1}$表示對於$u$子樹內的點除$u$之外度數都不超過$x$,且$u$的度數不超過$x+flag$時的最小代價。

轉移考慮:對於一個點$v$,假設它的度數爲$d_v(d_v > x)$,那麼轉移到$f_{v,1}$的狀態中須要切掉$v$與其孩子的$d_v - x - 1$條邊,而轉移到$f_{v,0}$須要切掉$d_v - x$條邊。而對於$y \in ch_v$,切掉邊$(y,v)$意味着$f_v$從$f_{y,1}+val_y$轉移,不然從$f_{y,0}$轉移。因此初始默認答案爲$\sum\limits_{y \in ch_v} f_{y,0}$,對於全部孩子按照$f_{y,1}+val_y-f_{y,0}$從小到大排序,選擇前面若干條邊切掉進行轉移。

而後能夠發現:$\sum\limits_{i=1}^n d_i = 2(n-1)$即$\sum\limits_{i=0}^{n-1}\sum\limits_{j=1}^n [d_i > j] = 2(n-1)$。因此若是稱某一次詢問中必需要切掉相鄰的若干條邊的點爲重要點,則在全部詢問中,重要點的總和爲$2(n-1)$。

到這裏不難想到虛樹。對於每一次詢問創建虛樹。由於虛樹上沒法體現重要點與非重要點之間的邊,可是實際有可能會切掉這樣的邊,因此對於每個重要點用一個堆維護它和它非重要點孩子之間的邊的邊權。DP過程當中,若是某個點$x$與虛樹上$x$的孩子$y$在原樹上的距離超過$2$,則直接用$\min(f_{y,0} , f_{y,1} + val_y)$轉移$f_x$,不然像上面同樣先默認轉移$f_{y,0}$,而後把$f_{y,1} + val_y - f_{y,0}$丟進堆裏,用堆求前若干小轉移到$f_{x,0}$和$f_{x,1}$。

將詢問從小到大作,就能夠直接維護每一個重要點的非重要點兒子的堆。

Update:關於priority_queue,它的賦值操做彷佛跟元素個數有關(可是很是快?),大力賦值在菊花圖上會TLE,因此要用multiset對操做進行撤銷。

代碼

G. Get Ready for the Battle

答案的下界是$\lceil \frac{\sum\limits_{i=1}^m hp_i}{n} \rceil$,而構造題通常都會取到這個下界(要否則怎麼構造啊喂),因此考慮構造一種方式使得總攻擊次數達到下界。那麼咱們須要儘量少地浪費兵力,也就是說要儘量把全部敵人打到$0$血。

爲了構造的方便,咱們令攻擊方式爲:先全部軍隊一塊兒攻擊第一個敵人,當第一個敵人的血量$<n$時,讓一個前綴的軍隊攻擊第一個敵人,讓第一個敵人剛好達到$0$血,剩下的軍隊直接去攻擊第二個敵人。維護前綴和$sum_i$,也就是說對於$\forall i \in[1,m)$,要存在一個前綴的軍隊,它們的人數之和爲$sum_i \mod n$。不難想到一種可行方案:將全部$sum_i \mod n$排序獲得數組$b_i$,$b_0 = 0 , b_m = n$,則$s_ i = b_i - b_{i-1}$。

構造方案直接暴力模擬上面的攻擊方法。

代碼

H. Triple

一個暴力是$O(n2^kk)$的FWT,顯然跑不過

顯然地,對於三元組$A,B,C$,將其變爲$0,A \oplus B , A \oplus C$,把最後結果的下標異或上$A$,這二者獲得的結果等價。

那麼在初始的數組中,$F_0 = a , F_{A \oplus B} = b , F_{A \oplus C} = c$,FWT以後每一個位置必定會是$a+b+c,a+b-c,a-b+c,a-b-c$中的一個。

設暴力FWT以後所有乘起來獲得的某個位置的值爲$(a+b+c)^x(a+b-c)^y(a-b+c)^z(a-b-c)^w$,解出$x,y,z,w$就可求出FWT結果。

首先$x+y+z+w=n$,而後任意給$(a,b,c)$賦值不會改變$x,y,z,w$的值,那麼令$(a,b,c) = (0,1,0)$,將獲得的$F$數組加起來FWT。由於FWT的和等於和的FWT,故有$(a+b+c)x + (a+b-c)y + (a-b+c)z + (a-b-c)w = p$,其中$p$就是FWT後獲得的當前位置的值。對於$(a,b,c) = (0,0,1)$也作一遍。

如今有了$3$個方程,但$(a,b,c)=(1,0,0)(0,1,0)(0,0,1)$都出現過了,再取$(a,b,c)$都和這三個向量線性相關,因此要換一種思路。考慮數組$G$,$G[x] = \sum\limits_{i=1}^n [B_i \oplus C_i = x]$,對這個數組FWT,能夠獲得$x-y-z+w=q$,其中$q$是FWT完成以後的點值表示。

緣由大概是:設序列$F$FWT後的序列爲$F'$,那麼$F[b]$對$F'[a]$的貢獻的係數是$(-1)^{count(a & b)}$,其中$count(x) = x$在二進制下$1$的個數,這個能夠由FWT的式子獲得。若是第$i$個三元組FWT以後第$j$位的值爲$a-b+c$,那麼有$2 \not\mid count((A \oplus B) & j) , 2 \mid count((A \oplus C) & j)$,即$2 \not\mid count((B \oplus C) & j)$,那麼$F[B \oplus C]$對$F'[j]$的貢獻就是$-1$,其他同理。

那麼如今獲得了$4$個方程組,能夠求出點值表示,最後IFWT一下。

代碼

BONUS:能夠利用與上面相似的方法解決更通常的對於$m$元組、$A,B,C < 2^k$的問題,複雜度約爲$O(2^{m+k}(m+k)+nm)$。

相關文章
相關標籤/搜索