bzoj 1758
參考部落格給出乙個 \(n\) 個節點帶邊權的樹,要求找出一條邊數在 \([l,u]\) 之間的路徑使得 \(\dfrace(w)}\) 最大
\(n\le100000,1\le l\le u\le n-1,v_i\le1000000\)
40sec,128mb
首先01分數規劃轉判斷問題,現在我們每個邊有新的邊權,我們要求樹上邊權最大的一條邊數 \([l,u]\) 的路徑
因為與深度有關,可以使用長鏈剖分解決,現在要用線段樹維護乙個區間最值,那麼之前的指標實現移位就無法使用了,考慮陣列只會向右移位**移方程為 \(f(v,j)->f(u,j+1)\)),那麼可以採用另一種移位方法,將樹剖分成鏈,那麼\(f(u,j)\) 的值就儲存在 \(val(dfn[u]+j)\) 位置,對 \(val\) 陣列維護乙個線段樹就好了
#include #include #include using namespace std;
inline char nc()
templatevoid read(t & x)
while(ch>='0'&&ch<='9')
x *= f;
}#define lson u << 1, l, mid
#define rson u << 1 | 1, mid + 1, r
const double eps = 1e-5;
const double infty = 1e18;
const int maxn = 100000 + 5;
const int maxe = maxn * 2;
const int maxv = 1000000 + 5;
int n, l, u; double an;
int head[maxn], ecnt;
double mid;
int dfn[maxn], len[maxn], son[maxn], cost[maxn], dfc;
double r[maxn];
struct edge
} g[maxe];
struct segment_tree
void build(int u, int l, int r)
int mid = (l + r) >> 1;
build(lson), build(rson);
pushup(u);
} void update(int u, int l, int r, int qp, double qv)
int mid = (l + r) >> 1;
if(qp <= mid) update(lson, qp, qv);
else update(rson, qp, qv);
pushup(u);
} double query(int u, int l, int r, int ql, int qr)
int mid = (l + r) >> 1;
if(qr <= mid) return query(lson, ql, qr);
else if (ql > mid) return query(rson, ql, qr);
else
}} seg;
inline void addedge(int u, int v, int w)
void dfs1(int u, int fa) }}
void dfs2(int u, int fa)
for(int i = head[u]; ~ i; i = g[i].nex)
} double query(int u, int l, int r)
void dp(int u, int fa, double dis)
seg.update(1, 1, n, dfn[u], dis);
for(int i = head[u]; ~ i; i = g[i].nex)
for(int j = 0; j <= len[v]; ++j)
} an = max(an, query(u, l, u) - dis);
}bool judge()
double solve()
return l;
}int main()
dfs1(1, 0), dfs2(1, 0);
printf("%.3lf\n", solve());
return 0;
}
BZOJ1758 WC2010 重建計畫
description input 第一行包含乙個正整數n,表示x國的城市個數.第二行包含兩個正整數l和u,表示政策要求的第一期重建方案中修建道路數的上下限 接下來的n 1行描述重建小組的原有方案,每行三個正整數 a i,b i,v i 分別表示道路 a i,b i 其價值為 v i 其中城市由1....
BZOJ 1758 Wc2010 重建計畫
要求平均值最大,二分平均值,判定是否存在一條合法路徑權值為正數,點分治 單調佇列 看上去沒有任何問題,然而其實每次點分的時候要按子樹深度從小到大排序然後更新答案 複雜度o n log 2 n 這個東西交上去又t了,然後學習了一下分數規劃怎麼二分,發現了一點神奇的方法,交上去又t了 可能我自己寫炸了 ...
WC2010 重建計畫
嘟嘟嘟 要不這篇部落格我水一下?思路很顯然,點分治 01分數規劃 單調佇列。但就是難寫。點分治的時候我們把每乙個點到重心這條鏈按深度排序,然後對於每乙個點的鏈就有乙個連續深度的區間可以和這條鏈拼上,因為要找一條權值大於 0 的鏈,那就相當於找這個區間的最大值。然後隨著點深度遞增,這個區間就不斷向左移...