左偏樹的題。
把每個節點上有的騎士按照攻擊力的大小建乙個小根堆。dfs的時候把兒子們的都合併過來,看看update完了的值是否小於防禦值。小於的話就pop,然後ans[x]++。記得開long long
#include #include #include using namespace std;
#define int long long
const int n=300005;
int n,m,h[n],s[n],c[n],tagx[n],tagj[n],nxt[n],to[n],a[n],v[n],head[n],ecnt,ls[n],rs[n],val[n],dis[n],ans[n],fa[n],dep[n],rt[n];
inline void add(int bg,int ed)
void update(int x,int mul,int ad)
inline void pushdown(int x)
int merge(int x,int y)
int pos[n];
void dfs(int x)
while(rt[x]&&val[rt[x]]if(a[x]) update(rt[x],v[x],0);
else update(rt[x],1,v[x]);
}main()
dep[1]=1;
dfs(1);
for(int i=1;i<=n;i++) printf("%lld\n",ans[i]);
for(int i=1;i<=n;i++) printf("%lld\n",dep[c[i]]-dep[pos[i]]);
return 0;
}
JLOI2015 城池攻占
霧.改變操作乘法是沒有負數的,那麼就不會改變大小關係,我們就可以dfs樹,然後用可合併堆進行操作。splay 啟發式合併也可以過 luogu 3261 bzoj 4003 include include include define int long long const int maxm 3100...
JLOI2015 城池攻占
點此看題 先把每個人放到對應的點上,可以用左偏樹,然後從下往上合併,每次就刪除當前節點會犧牲的人,然後維護乙個 加法 乘法 標記,時間複雜度o n log n o n log n o nlogn include include using namespace std define int long ...
JLOI2015 城池攻占
原題位址 首先發現乘的時候 係數不會為負,所以能得到乙個關鍵條件 變化後的戰鬥力隨變化前的戰鬥力大小單調 所以我們考慮倍增 設hp x i 是從x開始一路攻克 2 i 個城池所需要最小的初始生命值 設trans x i 0 1 是攻克了 2 i 個城池後攻擊力的變化量,0表示乘,1表示加,先乘後加 ...