传送门

设 $f[x][i]$ 表示 $x$ 的子树中,离 $x$ 最近的选择的节点距离为 $i$ 的合法方案的最大价值

设 $val[x]$ 表示节点 $x$ 的价值,首先有 $f[x][0]=val[x]$

那么考虑子树的合并,有 $f[x][min(i,j+1)]=max(f[x][min(i,j+1)],f[x][i]+f[v][j])$

注意此时 $f[x][i]$ 不能包括 $v$ 的贡献,这个可以搞个 $tmp$ 存一下新的 $f[x]$,最后统一覆盖掉即可

然后答案就是 $f[rt]$ 里面的状态取个最大值

复杂度 $n^3$

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
#include<vector>
using namespace std;
typedef long long ll;
inline int read()
{
int x=,f=; char ch=getchar();
while(ch<''||ch>'') { if(ch=='-') f=-; ch=getchar(); }
while(ch>=''&&ch<='') { x=(x<<)+(x<<)+(ch^); ch=getchar(); }
return x*f;
}
const int N=;
int n,m,val[N];
int fir[N],from[N<<],to[N<<],cntt;
inline void add(int a,int b) { from[++cntt]=fir[a]; fir[a]=cntt; to[cntt]=b; }
int f[N][N],tmp[N],ans;
vector <int> son[N];
void dfs(int x,int fa)
{
f[x][]=val[x];
for(int i=fir[x];i;i=from[i])
{
int &v=to[i]; if(v==fa) continue;
dfs(v,x); memset(tmp,,sizeof(tmp));
for(int j=;j<=n;j++)
for(int k=;k<=n;k++)
if(j+k+>m) tmp[min(j,k+)]=max(tmp[min(j,k+)],f[x][j]+f[v][k]);
for(int j=;j<=n;j++) f[x][j]=tmp[j];
}
}
int main()
{
n=read(),m=read(); int a,b;
for(int i=;i<=n;i++) val[i]=read();
if(n==) { printf("%d\n",val[]); return ; }
for(int i=;i<n;i++)
a=read(),b=read(),
add(a,b),add(b,a);
dfs(,);
for(int i=;i<=n;i++) ans=max(ans,f[][i]);
printf("%d\n",ans);
return ;
}

Codeforces 1249 F. Maximum Weight Subset的更多相关文章

  1. F. Maximum Weight Subset(贪心or树形dp解法)

    题:https://codeforces.com/contest/1249/problem/F 题意:给一颗树,边权为1,节点有点权,问取到一个点集,俩俩之间路径超过k,是点权和最大 思路:贪心地取点 ...

  2. CF1249F Maximum Weight Subset

    CF1249F Maximum Weight Subset 洛谷评测传送门 题目描述 You are given a tree, which consists of nn vertices. Reca ...

  3. codeforces#1249F. Maximum Weight Subset(树上dp)

    题目链接: http://codeforces.com/contest/1249/problem/F 题意: 一棵树的每个节点有个权值,选择一个节点集,使得任意点对的距离大于$k$ 求最大节点集权值, ...

  4. Codeforces 1249F Maximum Weight Subset (贪心)

    题意 在一颗有点权的树上,选若干个点,使得这些点两两距离大于k,且点权和最大 思路 贪心的取比较大的值即可 将所有点按照深度从大到小排序,如果当前点点权\(a[i]\)大于0,则将距离为k以内的所有点 ...

  5. 【CF1249F】Maximum Weight Subset(贪心)

    题意:给定一棵n个点带点权的树,要求从中选出一个点集,使得这些点两两之间距离都大于K,求最大点权和 n,K<=2e2,1<=a[i]<=1e5 思路:树形DP显然可做,极限是n方,然 ...

  6. Codeforces Round #555 (Div. 3) F. Maximum Balanced Circle

    F. Maximum Balanced Circle 题目链接 题意 给出\(n\)个数,现在要从中选出最多的数\(b_i,b_{i+1},\cdots,b_k\),将这些数连成一个环,要求两两相邻的 ...

  7. Codeforces 828F Best Edge Weight - 随机堆 - 树差分 - Kruskal - 倍增算法

    You are given a connected weighted graph with n vertices and m edges. The graph doesn't contain loop ...

  8. Codeforces 959 F. Mahmoud and Ehab and yet another xor task

    \(>Codeforces\space959 F. Mahmoud\ and\ Ehab\ and\ yet\ another\ xor\ task<\) 题目大意 : 给出一个长度为 \ ...

  9. Codeforces 835 F. Roads in the Kingdom

    \(>Codeforces\space835 F. Roads in the Kingdom<\) 题目大意 : 给你一棵 \(n\) 个点构成的树基环树,你需要删掉一条环边,使其变成一颗 ...

随机推荐

  1. qt mvc2

    继续上次的例子,对于list才说只有行,讨论列是没有意义的. bool insertRows(int row, int count, const QModelIndex &parent); b ...

  2. Socket函数详解

    #include <sys/types.h>; #include <sys/socket.h>; --------------------------------------- ...

  3. linux too many files

    Too many open files这个问题主要指的是进程企图打开一个文件,或者叫句柄,但是现在进程打开的句柄已经达到了上限,已经无法打开新句柄了. 网上一提到这个问题就要增加句柄上限,而往往这种情 ...

  4. Android 使用Intent

    使用intent可以吊起其他应用 例如发送电子邮件 public void sendEmail(View view){ Intent intent = new Intent(Intent.ACTION ...

  5. PorterDuffXfermode之Mode.SRC_IN

    package com.loaderman.customviewdemo.view; import android.content.Context; import android.graphics.B ...

  6. django模型多对多调用

    对于如下的模型: from django.db import models # Create your models here. class Student(models.Model): name = ...

  7. PHP判断是否在微信内部浏览器访问

    <?php if(is_weixin()){ echo "这是微信内部浏览器"; }else{ echo "这是微信外部浏览器"; } function ...

  8. MySQL数据库备份之mysqldump

    创建用户备份的用户 MariaDB [mysql]> create user 'backdata'@'localhost' identified by 'test@123456';Query O ...

  9. tornado之自定义form表单验证

    直接上链接吧:银角的地址 源码下载链接:点我点我点我...

  10. PAT 甲级 1061 Dating (20 分)(位置也要相同,题目看不懂)

    1061 Dating (20 分)   Sherlock Holmes received a note with some strange strings: Let's date! 3485djDk ...