牛客编程巅峰赛S2第3场 - 青铜&白银&黄金 C Tree VI

牛牛打怪

https://ac.nowcoder.com/acm/contest/9246/A

根据题面,可以发现前面层都是完全二叉树,所以可以先预处理出,每一层的节点个数,然后一直往左生儿子,在加上当前节点后如果超过了总结点就返回,先序遍历是一直先往左走,所以需要预处理出当前节点之前的完全二叉树的节点个数,可以根据代码具体理解.

const long long N=1e5+10;
class Solution {
public:
    typedef long long ll;
    ll n=0;
    ll lim=0;
    ll cnt=0;
    ll tot=0;
    ll res=0;
    ll num[N];
    ll head[N];
    ll base[N],pre[N];
    struct Edge{
        int u,v;
    }edge[N<<1];
    void add(ll x, ll y) {
        edge[++tot].u=head[x];
        edge[tot].v=y;
        head[x]=tot;
    }
    void dfs(ll now, ll loc, ll fa, ll dep) {
        if(now!=1) {
            add(now, fa);
            add(fa, now);
        }
        for(ll i=1; i<=lim; ++i) {
            if(pre[dep]>=n || pre[dep]+lim*(loc-1)+i>n) return;
            dfs(++cnt,lim*(loc-1)+i,now,dep+1);
        }
    }
    void dfs_two(ll now, ll fa) {
        if(now!=1) res+=(num[now]^num[fa]);
        for(ll i=head[now]; i; i=edge[i].u) {
            int to=edge[i].v;
            if(to==fa) continue;
            dfs_two(to,now);
        }
    }
    ll tree6(int k, vector<int>& a) {
        n=a.size();
        lim=k*1ll;
        for(int i=0; i<n; ++i) num[i+1]=a[i]*1ll;
        pre[0]=base[0]=1;
        for(int i=1; i<=n; ++i) base[i]=base[i-1]*lim;
        for(int i=1; i<=n; ++i) pre[i]=pre[i-1]+base[i];
        dfs(++cnt,1,0,0);
        dfs_two(1,0);
        return res;
   }
};
全部评论

相关推荐

10-24 13:36
门头沟学院 Java
Zzzzoooo:更新:今天下午有hr联系我去不去客户端,拒了
点赞 评论 收藏
分享
已老实求offer😫:有点像徐坤(没有冒犯的意思哈)
点赞 评论 收藏
分享
评论
3
收藏
分享
牛客网
牛客企业服务