Codeforces Round 974 (Div. 3) (D-H)
D
一眼看上去以为是单调栈单调队列啥的,但是实际上有区别()
E
两个单源最短路叠加是见过这种题的,枚举相遇点即可。
区别就是有🐎。想的是直接设多设两个状态求有🐎和没🐎的最小dis。
F
树形dp
不加强父节点的时候直接贪心,加强父节点时如果选加强的子节点需要减去2c,挨个处理子节点就行,搞清楚相互影响关系就不难了
多来点这种题给我上上分
#include<bits/stdc++.h>
using namespace std;
#define int long long
#define pii pair<int,int>
#define piib pair<int,pair<int,bool> >
#define mkp make_pair
#define endl ("\n")
const int maxn=2e5+10;
int tt;
int a[maxn],f[maxn][2],n,c;
vector<int>E[maxn];
void dfs(int x,int fa){
f[x][1]+=a[x];
for(auto i:E[x]){
if(i==fa)continue;
dfs(i,x);
f[x][0]+=max(f[i][0],f[i][1]);
f[x][1]=max(f[x][1]+f[i][0],f[x][1]+f[i][1]-c*2);
}
return;
}
void solve(){
cin>>n>>c;
for(int i=1;i<=n;i++){
cin>>a[i];E[i].clear();
f[i][1]=0;f[i][0]=0;
}
for(int i=1;i<n;i++){
int u,v;cin>>u>>v;
E[u].push_back(v);
E[v].push_back(u);
}
dfs(1,0);
cout<<max(f[1][0],f[1][1])<<endl;
}
signed main(){
ios::sync_with_stdio(false);
cin>>tt;while(tt--)solve();
}
G
没看