最大利润问题(深搜+树形DP)

版权声明:个人博客:www.jingyile.cn 萌新发博文积累经验,欢迎各位大佬指导!!! https://blog.csdn.net/JYL1159131237/article/details/78293718

解题思路:

   1)用邻接表表示这颗树;
(2)先进行深搜查找到叶子节点,然后从叶子节点返回到父节点;
(3)主要思想:深度优先搜索+动态规划

    

代码:

#include<stdio.h>
struct node
{
    int to;
    int next;
}a[200005];//定义邻接表
int dp[100005][2];
int vis[100005];//标记是否被访问过
int head[200005];
int n;
int top;
int max(int a,int b)
{
    return a>b?a:b;
}

void dfs(int v)
{
    int i;
    vis[v]=1;//将当前节点置为已访问
    for(i=head[v];i;i=a[i].next)//穷举与当前节点相连的每一个节点
        if(!vis[a[i].to])//如果当前节点未被访问
    {
        dfs(a[i].to);//对子节点进行深搜
        dp[v][1]+=dp[a[i].to][0];
        dp[v][0]+=max(dp[a[i].to][0],dp[a[i].to][1]);
    }
}
void creat(int x,int y)//形成邻接表
{
    a[++top].to=y;//当前的下一个节点
    a[top].next=head[x];//当前边的序号
    head[x]=top;//序号+1
}

int main()
{
    int i,x,y;
    scanf("%d",&n);
    for(i=1;i<=n;i++)
        scanf("%d",&dp[i][1]);
    for(i=0;i<n-1;i++)
    {
        scanf("%d%d",&x,&y);
        creat(x,y);//对x和y建立一条边
        creat(y,x);
    }
    dfs(1);//以第一个节点为根进行深搜
    printf("%d",max(dp[1][0],dp[1][1]));
    return 0;
}
学习心得:这道题用到的知识点还是很多的,比如关于邻接表的的使用及它的数组实现。

一道树形DP的题,关于这些还是很陌生的,要多看多练才行。

展开阅读全文

没有更多推荐了,返回首页