bzoj十連測第二場 A 深邃

2021-07-14 09:52:21 字數 1108 閱讀 7625

一棵樹每個節點有顏色。

請將樹分成若干連通塊,使每個連通塊均包含黑點。最小化最大的連通塊的大小。

看到雙最直接二分。

二分了乙個k,接下來怎麼判定?

設f[i]表示以i為根的情況:

1、f[i]為正數,表示以i為根的子樹內除了i所在連通塊均合法,i所在連通塊包含黑點時i所處連通塊大小的最小值。

2、f[i]為負數,表示以i為根的子樹內除了i所在連通塊均合法,i所在連通塊不包含黑點時i所處連通塊大小的相反數的最大值。

於是,我們樹形dp,如果x是黑點,則所有f為負的與其乙個連通塊,然後f[x]為正。如果x是白點,那麼我們找到其子樹中f為正最小的,如果帶上這個子樹大小不超過k則帶上f[x]為正,否則不能帶上f[x]為負,具體見**。

注意存在任意乙個f[x]其絕對值超過k就非法。

#include

#include

#define fo(i,a,b) for(i=a;i<=b;i++)

using

namespace

std;

const

int maxn=200000+10;

int f[maxn],h[maxn],go[maxn*2],next[maxn*2];

bool bz[maxn],czy;

int i,j,k,l,r,mid,t,n,m,tot,top,ans,x,y,z,u,v,w;

void add(int x,int y)

void dfs(int x,int y)

t=next[t];

}if (bz[x]) f[x]=l+1;

else

if (k+l+1

<=mid) f[x]=k+l+1;

else f[x]=-l-1;

if (abs(f[x])>mid) czy=0;

}bool check()

int main()

fo(i,1,m)

l=1;r=n;

while (l2;

if (check()) r=mid;else l=mid+1;

}printf("%d\n",l);

}

BZOJ十連測 線段樹

在若干次操作後,某乙個位置的值可以表示成若干各區間的最大值。例如位置k kk,我們找到當前操作前最後乙個 編號最大但小於當前編號 覆蓋當前區間左端點的操作的左端點,最後乙個覆蓋當前當前區間右端點的操作的右端點,把這個左右端點當成乙個新的操作區間,然後重複執行上述操作。也就是我們需要一直向左找,一直向...

bzoj十連測第三場 A 哈夫曼樹

和的期望 期望的和。因此計算每個節點期望貢獻再加起來即可。乙個結點的期望深度與其數值大小和所在陣列位置無關,因此可以一視同仁。假設還有i顆子樹,我們顯然知道乙個結點肯定處於一顆子樹內。只有在該輪其所在子樹被合併時深度才會加一,所以貢獻為被合併的概率 1。被合併的概率是i 1c2i 2i 所以答案就是...

BZOJ 2017省隊十連測推廣賽1

聽學長說有比賽就隨便打一打。a.普通計算姬 題目大意 給出一棵帶權樹,支援一下兩種操作 1.修改乙個點的權值 2.給出l,r,詢問以點l為根的子樹和 點l 1為根的子樹和 點l 2為根的子樹和 點r為根的子樹和的總和。點數 運算元不超過10 5 思路 感覺是三題中最難的。給出的 l,r 區間在樹上沒...