【无标题】

树上求最大上升子序列 Login - Codeforces

##C<https://codeforces.com/gym/489511/problem/C>

##思路

**最大上升子序列+用链式前向星存搜多叉树**

**借鉴大佬的代码 一开始傻傻的每个点跑一次dfs查路径 最大上升子序列也难求 注意区分字串和子序列 子序列可跳点**

##代码
```cpp
#include<bits/stdc++.h>
using namespace std;
int n;
int a[100005];
int head[100005];//以i为起点的最后一条边的编号
int cnt;
struct ad {
    int from;
    int to;
}e[200005];//双向边
void add(int x, int y) {
    cnt++;
    e[cnt].from = head[x];
    e[cnt].to = y;
    head[x] = cnt;
}
int ans[100005];//dfs时记录答案
int s[100005];//最大上升子序列 维护
int l;//维护数组的尾巴
void dfs(int t, int f) {
    int ops = lower_bound(s + 1, s + l + 1,a[t]) - s;//新进来一个数 贪心地加入它
    int tmp = s[ops];//记录 用于回溯
    s[ops] = a[t];
    int fg = 0;//也是记录用于回溯
    if (ops == l + 1) {//正好加在最后
        l++;
        fg = 1;
    }
    ans[t] = l;//最长就在尾巴
    for (int i = head[t]; i; i = e[i].from) {
        int t1 = e[i].to;//遍历这一层 以t为起点的边
        if (t1 == f) continue;//回边
        dfs(t1, t);
    }
    if (fg == 1) l--;//这一层搜完了 往上面回溯 恢复改变量
    s[ops] = tmp;//恢复
}
int main()
{
    cin >> n;
    for (int i = 2; i <= n; i++) {
        int x;
        cin >> x;
        add(i, x), add(x, i);
    }
    for (int i = 1; i <= n; i++) cin >> a[i];
    dfs(1, 0);
    for (int i = 2; i <= n; i++) cout << ans[i] << " ";
    return 0;
}
```

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值