「题解」水库 reservoir
Posted Lu_Anlai
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了「题解」水库 reservoir相关的知识,希望对你有一定的参考价值。
本文将同步发布于:
题目
题目描述
R 国有 \\(n\\) 座城市和 \\(n-1\\) 条长度为 \\(1\\) 的双向道路,每条双向道路连接两座城市,城市之间均相互连通。
现在你需要维护 R 国的供水系统。你可以在一些城市修建水库,在第 \\(i\\) 个城市修建水库需要每年 \\(c_i\\) 的维护费用。对于没有修建水库的城市,如果离它最近的水库的距离为 \\(d\\),那么需要每年 \\(t_d\\) 的运输费用来保证该城市的用水需求。保证 \\(t_i\\) 严格递增。
你的任务是计算出每年所需要的最小花费。
\\(1\\leq n\\leq 10^3\\),\\(0\\leq c_i,t_i\\leq 10^5\\)。
题解
很简单的树形动态规划。
设 \\(f_{i,j}\\) 表示,以 \\(i\\) 为根的子树,\\(i\\) 的供水依赖于 \\(j\\) 所需的最小花费,\\(g_i\\) 为 \\(i\\) 的子树,不论 \\(i\\) 依赖于谁的最小花费。
那么我们有:
\\[f_{i,j}=t_{\\texttt{dis}_{i,j}}+c_j+\\sum_{k\\in\\texttt{son}_i}\\min\\{f_{k,j}-c_j,g_k\\}
\\]
\\[g_i=\\min_{j=1}^n\\{f_{i,j}\\}
\\]
直接动态规划即可,时间复杂度为 \\(\\Theta(n^2)\\)。
参考程序
#pragma GCC optimize("Ofast")
#include<bits/stdc++.h>
using namespace std;
#define reg register
typedef long long ll;
#define getchar() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++)
static char buf[1<<21],*p1=buf,*p2=buf;
inline int read(void){
reg char ch=getchar();
reg int res=0;
while(!isdigit(ch)) ch=getchar();
while(isdigit(ch)) res=10*res+(ch^\'0\'),ch=getchar();
return res;
}
inline int min(reg int a,reg int b){
return a<b?a:b;
}
const int MAXN=1e3+5;
const int inf=0x3f3f3f3f;
int n;
int c[MAXN],t[MAXN];
vector<int> G[MAXN];
int dis[MAXN][MAXN];
inline void getDis(reg int u,reg int father,reg int rt,reg int dep){
dis[rt][u]=dep;
for(int v:G[u])
if(v!=father)
getDis(v,u,rt,dep+1);
return;
}
int f[MAXN][MAXN];
int g[MAXN];
inline void dfs(reg int u,reg int father){
for(reg int i=1;i<=n;++i)
f[u][i]=t[dis[u][i]]+c[i];
for(int v:G[u])
if(v!=father){
dfs(v,u);
for(reg int i=1;i<=n;++i)
f[u][i]+=min(f[v][i]-c[i],g[v]);
}
g[u]=inf;
for(reg int i=1;i<=n;++i)
g[u]=min(g[u],f[u][i]);
return;
}
int main(void){
n=read();
for(reg int i=1;i<=n;++i)
c[i]=read();
for(reg int i=1;i<=n;++i)
t[i]=read();
for(reg int i=1;i<n;++i){
static int s,t;
s=read(),t=read();
G[s].push_back(t),G[t].push_back(s);
}
for(reg int i=1;i<=n;++i)
getDis(i,0,i,0);
dfs(1,0);
printf("%d\\n",g[1]);
return 0;
}
以上是关于「题解」水库 reservoir的主要内容,如果未能解决你的问题,请参考以下文章
Reservoir Sampling-382. Linked List Random Node