【bzoj3227】紅黑樹
阿新 • • 發佈:2017-05-14
發現 blog ret amp 這樣的 spa 兩個 include log
神TM的紅黑樹,其實本質上應該還是一種樹dp的問題……
一開始想了一個比較裸的樹dp,後來發現還有更強的做法。
每個前端黑節點是看作一個物品,然後這就是很典型的樹形dp的問題。
不過可以這麽考慮,考慮怎麽縮小問題的範圍。
我們可以把黑色節點的連通塊縮成一個點,這樣的話就要考慮三個情況:
- 直接合並兩個相鄰的黑色節點
- 將三個黑節點合並為一紅一黑
- 將四個黑節點合並為兩紅一黑
所以直接貪心就能做。
#include<bits/stdc++.h> using namespace std; int n,m,ans; inline int read(){ int f=1,x=0;charch; do{ch=getchar();if(ch==‘-‘)f=-1;}while(ch<‘0‘||ch>‘9‘); do{x=x*10+ch-‘0‘;ch=getchar();}while(ch>=‘0‘&&ch<=‘9‘); return f*x; } int main(){ n=read();m=n+1; while(m>1){if(m&1)ans++;m>>=1;} printf("%d\n",ans); m=n+1;ans=0; while(m>1){if(m==2)ans++; if((m&3)==1)ans+=(m>>2)*2-1,m>>=2,m++; else if((m&3)==2)ans+=(m>>2)*2,m>>=2,m++; else if((m&3)==3)ans+=(m>>2)*2+1,m>>=2,m++; else if(!(m&3))ans+=(m>>2)*2,m>>=2; } printf("%d\n",ans); }
【bzoj3227】紅黑樹