zoukankan      html  css  js  c++  java
  • [CF600E]Lomsat gelral

    题意翻译

    一棵树有n个结点,每个结点都是一种颜色,每个颜色有一个编号,求树中每个子树的最多的颜色编号的和。

    线段树合并板子题,没啥难度,注意开long long

    不过这题$dsu$ $on$ $tree$确实更快

    代码:

     1 #include<iostream>
     2 #include<cstdio>
     3 #define ls ch[node][0]
     4 #define rs ch[node][1]
     5 #define M 100010
     6 using namespace std;
     7 int n,m,num,cnt;
     8 int head[M],rt[M],co[M];
     9 int ch[M<<7][2],v1[M<<7];
    10 long long v2[M<<7],ans[M];
    11 struct point{int to,next;}e[M<<1];
    12 void add(int from,int to) {
    13     e[++num].next=head[from];
    14     e[num].to=to;
    15     head[from]=num;
    16 }
    17 void update(int node) {
    18     if(v1[ls]==v1[rs]) {
    19         v1[node]=v1[ls];v2[node]=v2[ls]+v2[rs];
    20     }
    21     else{
    22         if(v1[ls]>v1[rs]) v1[node]=v1[ls],v2[node]=v2[ls];
    23         else v1[node]=v1[rs],v2[node]=v2[rs];
    24     }
    25 }
    26 void insert(int &node,int l,int r,int x) {
    27     if(!node) node=++cnt;
    28     if(l==r) {
    29         v1[node]=1,v2[node]=x;return;
    30     }int mid=(l+r)/2;
    31     if(x<=mid) insert(ls,l,mid,x);
    32     else insert(rs,mid+1,r,x);
    33     update(node);
    34 }
    35 int merge(int x,int y,int l,int r) {
    36     if(!x||!y) return x+y;
    37     int node=++cnt;
    38     if(l==r) {
    39         v1[node]=v1[x]+v1[y];v2[node]=l;return node;
    40     }
    41     int mid=(l+r)/2;
    42     ch[node][0]=merge(ch[x][0],ch[y][0],l,mid);
    43     ch[node][1]=merge(ch[x][1],ch[y][1],mid+1,r);
    44     update(node);return node;
    45 }
    46 void dfs(int x,int fa) {
    47     insert(rt[x],1,n,co[x]);
    48     for(int i=head[x];i;i=e[i].next) {
    49         int to=e[i].to;
    50         if(to==fa) continue;
    51         dfs(to,x);
    52         rt[x]=merge(rt[x],rt[to],1,n);
    53     }
    54     ans[x]=v2[rt[x]];
    55 }
    56 int main() {
    57     scanf("%d",&n);
    58     for(int i=1;i<=n;i++) scanf("%d",&co[i]);
    59     for(int i=1;i<n;i++) {
    60         int x,y;scanf("%d%d",&x,&y);
    61         add(x,y),add(y,x);
    62     }
    63     dfs(1,0);
    64     for(int i=1;i<=n;i++) printf("%lld ",ans[i]);
    65     return 0;
    66 }
  • 相关阅读:
    解决:transform-decorators-legacy 报错
    leetcode刷题笔记 232题 用栈实现队列
    leetcode刷题笔记 231题 2的幂
    leetcode刷题笔记 230题 二叉搜索树中第K小的元素
    leetcode刷题笔记 229题 求众数II
    leetcode刷题笔记 228题 汇总区间
    leetcode刷题笔记 227题 基本计算器II
    leetcode刷题笔记 225题 用队列实现栈
    leetcode刷题笔记 224题 基本计算器
    leetcode刷题笔记 223题 矩形面积
  • 原文地址:https://www.cnblogs.com/Slrslr/p/10043248.html
Copyright © 2011-2022 走看看