Codecraft-18 and Codeforces Round #458 E. Palindromes in a Tree(点分治)

网络流题目合集 属实狠活 HDU 2883 kebab还是区间k重覆盖的变形,然而每想到 就这? HDU 3315 My Brute HDU 3947 River Problem 区间k重覆盖的变形 拉了 阅读详情

题意:

     一棵树,每个点都有一个字母,如果一条路径的字符的某个排列是回文串,就称这个路径是回文的,问经过每个点的回文路径有多少条

思路:

     很明显的点分治。首先因为字母是a到t,所以可以状压一下,利用异或来改变路径的状态,那么任意一个路径都可以用一个值来表示,如果一个值的二进制中1的个数小于等于1,那么这个路径就是回文的(利用__builtin_popcount函数)。
    然后根据树分治的思想,我们选取了一个重心,我们先把以重心为根,所有子树的所有路径通过状压后的值用一个数组记录数量。我们这里要做的,就是统计通过某个点的回文路径有多少条。当我们要算某个子树的贡献时,我们就先删去这个子树的所有的路径的值的贡献,然后统计答案,统计完了再把这些值放回去。
     但是存在一个问题,就是当我们发现dfs到某个点的时候,路径构成的值可以构成一个回文路径时,需要把重心到这个点的路径上的所有点的答案都加上一个值。这里可以通过dfs的时候顺便记录子树的贡献,记录完后把值返还给父亲即可。
     剩下的就是一些小细节了(其实细节还蛮多的),写的时候注意一下即可

错误及反思:

代码:

#include<bits/stdc++.h>
using namespace std;
const int N = 200100;

struct EDGE{
    int to,next;
}e[N*2];
int first[N],n,tot,si[N],maxn[N],k;
long long ans[N];
bool did[N];
char s[N];
long long m[2000000];
vector<int> v;

void addedge(int x,int y){
    e[tot].to=y;
    e[tot].next=first[x];
    first[x]=tot++;
    e[tot].to=x;
    e[tot].next=first[y];
    first[y]=tot++;
}

void dfs_size(int now,int fa){
    si[now]=1;
    maxn[now]=0;
    for(int i=first[now];i!=-1;i=e[i].next)
        if(e[i].to!=fa&&!did[e[i].to]){
            dfs_size(e[i].to,now);
            si[now]+=si[e[i].to];
            maxn[now]=max(maxn[now],si[e[i].to]);
        }
}

void dfs_root(int now,int fa,int& root,int& nu,int t){
    int MA=max(maxn[now],si[t]-si[now]);
    if(MA<nu){
        nu=MA;
        root=now;
    }
    for(int i=first[now];i!=-1;i=e[i].next)
        if(e[i].to!=fa&&!did[e[i].to])
            dfs_root(e[i].to,now,root,nu,t);
}

void dfs2(int now,int fa,int tlen){
    for(int i=first[now];i!=-1;i=e[i].next)
        if(e[i].to!=fa&&!did[e[i].to])
            dfs2(e[i].to,now,tlen^(1<<(s[e[i].to]-'a')));
    v.push_back(tlen);
}

long long dfs3(int now,int fa,int tlen,int root){
    long long num=0;

    for(int i=first[now];i!=-1;i=e[i].next)
        if(e[i].to!=fa&&!did[e[i].to]){
            num+=dfs3(e[i].to,now,tlen^(1<<(s[e[i].to]-'a')),root);
        }

    ans[now]+=num;
    for(int k=0;k<20;k++){
        num+=m[(1<<k)^tlen^(1<<(s[root]-'a'))];
        ans[now]+=m[(1<<k)^tlen^(1<<(s[root]-'a'))];
    }

    num+=m[tlen^(1<<(s[root]-'a'))];
    ans[now]+=m[tlen^(1<<(s[root]-'a'))];

    return num;
}

long long dfs4(int now,int fa,int tlen,int root){
    long long num=0;
    for(int i=first[now];i!=-1;i=e[i].next)
        if(e[i].to!=fa&&!did[e[i].to]){
            num+=dfs4(e[i].to,now,tlen^(1<<(s[e[i].to]-'a')),root);
        }
    if(__builtin_popcount(tlen^(1<<(s[root]-'a')))<=1) num++;
    ans[now]+=num;
    return num;
}


void solve(int now){
    int root,nu=1e9;
    dfs_size(now,-1);
    dfs_root(now,-1,root,nu,now);
    did[root]=true;
    for(int i=first[root];i!=-1;i=e[i].next){
        if(!did[e[i].to]){
            v.clear();
            dfs2(e[i].to,root,(1<<(s[e[i].to]-'a')));
            for(int j=0;j<v.size();j++) m[v[j]]++;
        }
    }
    long long td=0;
    for(int i=first[root];i!=-1;i=e[i].next){
        if(!did[e[i].to]){
            v.clear();
            dfs2(e[i].to,root,(1<<(s[e[i].to]-'a')));
            for(int j=0;j<v.size();j++) m[v[j]]--;

            td+=dfs3(e[i].to,root,(1<<(s[e[i].to]-'a')),root);

            ans[root]+=dfs4(e[i].to,root,(1<<(s[e[i].to]-'a')),root);

            for(int j=0;j<v.size();j++) m[v[j]]++;
        }
    }
    ans[root]+=td/2;

    for(int i=first[root];i!=-1;i=e[i].next){
        if(!did[e[i].to]){
            v.clear();
            dfs2(e[i].to,root,(1<<(s[e[i].to]-'a')));
            for(int j=0;j<v.size();j++) m[v[j]]--;
        }
    }

    for(int i=first[root];i!=-1;i=e[i].next)
        if(!did[e[i].to])
            solve(e[i].to);
}


void init(){
    memset(first,-1,sizeof(first));
    tot=0;
}

int main(){
    scanf("%d",&n);
    init();
    for(int i=0,u,v;i<n-1;i++){
        scanf("%d%d",&u,&v);
        addedge(u,v);
    }
    scanf("%s",s+1);
    solve(1);
    for(int i=1;i<=n;i++) printf("%lld ",ans[i]+1);
}

【Godot4自学手册】第一节配置Godot运行环境 Godot是一款自由开源、由社区驱动的 2D 和 3D 游戏引擎!它是一款功能丰富的跨平台游戏引擎,可以通过统一的界面创建 2D 和 3D 游戏。它提供了一套全面的通用工具,因此用户可以专注于制作游戏,而无需重新发明轮子。游戏可以一键导出到多个平台,包括主流的桌面平台(Linux、macOS、Windows)、移动平台(Android、iOS)、基于 Web 的平台以及主机平台。 阅读详情

相关推荐

别再硬啃理论了!手把手教你用Simulink搭VSG并网模型,模拟线路故障(含三相故障模块详解)

本文提供了一份详细的Simulink VSG并网模型搭建指南,特别聚焦于三相故障模块的配置与仿真。通过逐步指导,帮助电力电子工程师掌握从基础电路搭建到复杂故障模拟的全流程,包括单相接地、两相短路等典型故障的波形分析与参数设置技巧,有效弥合理论与实践的鸿沟。

weixin_29057237的博客 317

Codeforces 914E Palindromes in a Tree 点分治

E. Palindromes in a Treetime limit per test4 secondsmemory limit per test256 megabytesinputstandard inputoutputstandard outputYou are given a tree (a connected acyclic undirected graph) of n vertices....

J. Cole 1091

【嵌入式Linux】EC20模块多运营商自适应PPP拨号实战:从IMSI识别到网络配置

本文详细介绍了在嵌入式Linux系统中,如何基于EC20 4G模块实现多运营商自适应PPP拨号。通过解析SIM卡的IMSI识别运营商,并动态配置对应的APN和拨号参数,结合AT指令交互与健壮的pppd脚本,解决了设备跨地域部署时的网络自动连接问题,提升了物联网设备的部署效率和稳定性。

fox11的博客 902

【CodeForces】914 E. Palindromes in a Tree 点分治

【题目】E. Palindromes in a Tree 【题意】给定一棵树,每个点都有一个a~t的字符,一条路径回文定义为路径上的字符存在一个排列构成回文串,求经过每个点的回文路径数。n<=2*10^5。 【算法】点分治 【题解】状压20位的二进制表示一条路径的字符状态,点分治过程中维护扫描过的路径只须维护状态桶数组,t[i]表示前面状态为i的路径条数。 合并:考虑当前状态为j,要...

weixin_34319817的博客 252

第三篇:学习InternVL2.0(探讨代码之训练模块版)

InternVL2的训练模块

qq_69051120的博客 1244

工程师必看:如何用功率谱密度搞定随机振动测试(附Grms计算实例)

本文为工程师详解如何通过功率谱密度(PSD)曲线计算Grms(总均方根加速度),从而量化随机振动测试的强度。文章拆解了平直谱、斜谱的计算公式,提供了完整的Grms计算实例,并指出了单位换算、对数坐标等常见工程陷阱,帮助工程师精准完成测试准备与设备推力评估。

3c4x5z6v7b的博客 625

Codeforces Round #315 (Div. 2) C. Primes or Palindromes? 素数表 回文数

C. Primes or Palindromes? time limit per test 3 seconds memory limit per test 256 megabytes input standard input output standard output Rikhail Mubinchik believes that t

习惯与规则决定命运 1349

FreeCAD MCP实战:用AI自然语言驱动CAD建模与自动化

在计算机辅助设计(CAD)领域,参数化建模和自动化脚本是提升设计效率的核心技术。其原理在于通过程序化指令控制三维模型的创建与修改,从而将设计意图转化为精确的几何实体。这种技术价值在于显著降低重复性操作成本,实现快速原型迭代和设计探索。在应用场景上,它尤其适用于需要频繁调整尺寸、生成系列化零件或执行规则化建模任务的工程与产品设计。本文聚焦的FreeCAD MCP项目,正是这一理念的先进实践。它通过集成Model Context Protocol(MCP),构建了一个连接Claude AI与FreeCAD的智能

weixin_26913055的博客 723

CF914E Palindromes in a Tree

$ \color{#0066ff}{ 题目描述 }$ 给你一颗 n 个顶点的树(连通无环图)。顶点从 1 到 n 编号,并且每个顶点对应一个在‘a’到‘t’的字母。 树上的一条路径是回文是指至少有一个对应字母的排列为回文。 对于每个顶点,输出通过它的回文路径的数量。 注意:从u到v的路径与从v到u的路径视为相同,只计数一次。 \(\color{#0066ff}{输入格式}\) 第一行包含一个整数n...

weixin_30393907的博客 242

基于STM32设计的智能家居控制系统(华为云)_363

本项目设计并实现了一种基于STM32的智能家居控制系统,融合了语音识别、远程控制、环境监测与安全报警等功能。系统以STM32F103C8T6单片机为核心控制器,集成ESP8266 Wi-Fi模块实现与华为云IOT物联网平台的数据交互,采用MQTT协议进行通信。用户可通过语音识别模块控制风扇、空调、窗帘、卧室灯、客厅灯和电视等家电的开关操作,同时也可通过Android手机APP或Windows电脑上位机进行远程控制。系统还具备温湿度、光照强度、烟雾浓度和火焰检测功能,当检测到异常情况时,自动触发蜂鸣器报警并向

881

将 SAP BTP ABAP environment 与 SAP S/4HANA Cloud 公有云版集成:从架构理念到落地实战

本文探讨了在SAP云环境中实现ABAP扩展应用与S/4HANA Cloud系统集成的技术方案。通过建立标准化的远程通信通道,开发者可在SAP BTP ABAP环境中开发扩展应用,同时安全访问S/4HANA Cloud的核心业务数据和服务。文章详细介绍了整体架构设计、开发实现步骤(包括定义通信场景、生成服务消费模型和编写调用代码)以及管理员在S/4HANA侧的配置工作(创建通信安排和技术用户)。通过一个业务伙伴自助注册平台的案例,展示了如何在不修改标准系统的情况下实现云扩展,体现了SAP"干净核心&

2007 年 ~ 2025 年,深耕 SAP 技术 18 年 239

Codecraft-18 and Codeforces Round #458 (Div. 1 + Div. 2, combined) E. Palindromes in a Tree(点分治)

题目链接:http://codeforces.com/contest/914/problem/E点分治,a到t只有20个字母,状压表示每个字母出现的奇偶性,然后点分治,计数的时候正着扫一边然后反着扫一边即可,然后就是打标记的小技巧,优化常数。代码:#include&lt;bits/stdc++.h&gt; using namespace std; typedef long long ll; nam...

bibibibi的博客 281

Python办公自动化 2.1开发环境搭建:PyCharm社区版配置Anaconda开发环境

本篇文章主要讲述了如何在windows主机上配置 PyCharm + Anaconda开发环境、以及了如何配置 PyQt界面开发环境,安装过程超级详细,初学者可以照着一步一步来!

超级大洋葱的博客 2584

NEERC 17 I Interactive Sort (交互题)

题意: &nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;给出1到n这n个数的任意一个排列,然后奇数按顺序分到o数组,偶数按顺序分到e数组,你每次可以询问e数组中第i个和o数组中第j个的大小情况,查询结束后输出结果,查询次数最多30 000次,n≥1000n≥1000n\ge1000 思路: &nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;我...

Roll_Keyboard的博客 705

温度PID控制PLC程序

温度PID稳定控制程序,适用于欧姆龙PLC,对其他PLC也具有很大参考价值

Devexpress16.2.6破解工具

Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具

NEERC 17 G The Great Wall (treap)

题意: &amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp; 给你一个数列,每个点有abc三个值,现在让你画两个区间x,y,区间大小为r,区间不可以完全重合,当一个点没有被区间覆盖时值为a,被一个区间覆盖时值为b,两个区间为c,问第k小的数列数值总和为多少 思路: &amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp

Roll_Keyboard的博客 694

Camera2Demo

在Camera2 的基础上进行封装,使得Camera2一堆初始化逻辑与Activity分离,降低耦合度,完成预览拍照并保存的操作

Codeforces 85D. Sum of Medians (线段树)

题意: &nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp; 三种操作,1.加入一个数,2,删除一个数,3,询问经过排序以后,所有下标mod5mod5mod5余3的数的和 思路: &nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp; 注意到,当我们加入一个数以后,会让所有后面的数后移一位,删除会使得后面全部前移一位,每次移动都使得下标变化1,所以我...

Roll_Keyboard的博客 652

精雕软件(JDpaint) 5.5 绿色版

精雕软件(JDpaint) 5.5 绿色版精雕软件(JDpaint) 5.5 绿色版精雕软件(JDpaint) 5.5 绿色版

Codeforces Round #437 (Div. 2) B. Save the problem!

题意:给你一个数字A,要你给出一个价格和一堆硬币种类,要让这些硬币组成这个价格的方案数为A思路:想了很久没想出来,答案是除了A是1的时候,价格都是2*(A-1),硬币只有1和2,因为,你用(A-1)个2元0个1元,然后是(A-2)个2个1元,这样方案数就相当于A-1减到0,共A种,真的有点巧妙。。。错误及反思:其实自己写个完全背包打表也许能看出规律吧,可惜完全没往这个方向想代码:#include<b

Roll_Keyboard的博客 634

Codeforces Round #104 (Div. 1) E. Lucky Queries (线段树)

题意: &nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp; 长度为n的47串,两种操作,一种是区间变换,即4变7,7变4,一种是询问,问最长的非严格递增子序列长度 思路: &nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp; 线段树维护即可,47可以抽象成01串,变换就是异或,存储全0串最长长度,全1串最长长度,000..111串长度,111…0...

Roll_Keyboard的博客 564

NEERC 17 L Laminar Family (树链剖分)

题意: &nbsp;&nbsp;&nbsp;&nbsp; 给你一颗树,每次选取一个路径,把路径上的所有点加入到一个集合里面,问最后的集合是否两两之间满足 A∈BA∈B A\in B 或者B∈AB∈AB\in A或者A∪B=∅A∪B=∅A\cup B = \emptyset 思路: &nbsp;&nbsp;&nbsp;&nbsp;我们发现,如果最后是符合条件的,那么必定是一个集合被另一个集合...

Roll_Keyboard的博客 549

Codeforces Round #437 (Div. 2)E. Buy Low Sell High(优先队列)

题意:给你n个数字,现在你可以有以下的操作,买一个数字,再在之后卖出去,问最多能赚多少钱思路:对于一个数字,如果之后的的数字如果比这个数字还大,那么我们可以当作之前买了一个,然后现在卖出去,可是这样的做法存在问题,比如1,2,3,66,按照那样的做法,我们的收益是2-1+66-3=64,然而66-1+3-2=66,很明显之前的做法存在错误,错误的核心在于对于买卖对象确认的错误 那么,如果我们把之前

Roll_Keyboard的博客 521

Codeforces Round #442 (Div. 2) F. Ann and Books (莫队算法+离散化)

题意:给你一n个数字,其中有的是第一类,有的是第二类,接着是m个查询,问你某个区间内,连续的子区间的第一类的和减去第二类的和恰好为k的子区间一共多少个。思路:莫队算法及离散化。这个题不是一般的毒,卡logn。 首先对于这个题目,只查询不修改,很容易想到莫队算法。首先处理出前缀和,那么我val[i]-val[j]就能表示aj+1+aj+2+...+ai{a_{j+1}+{a_{j+2}+...+{a

Roll_Keyboard的博客 471

codeforces 161D D. Distance in Tree (树分治)

题意:问一颗树有多少个路径距离为k思路:是poj1741的简单版,在树分治的时候,对于某个重心只要维护某个长度的有多少即可,因为k很小,所以可以直接开个数组存错误及反思:中间加的过程忘了会爆int了。。。代码:#include<bits/stdc++.h> #define fi first #define se second using namespace std; const int N = 50

Roll_Keyboard的博客 462

Codeforces Daily (Round 370-410)

—————————————————————————- 时间:8.1 &amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;amp;am

Roll_Keyboard的博客 460

Codeforces Round #301 (Div. 2) D. Bad Luck Island(概率dp)

题意:有n个石头,m个剪刀,k个布,每次会等概率的两个对决,胜利的留下,失败的离开,问最后剩下的全是石头,全是剪刀或全是布的概率思路:利用概率dp求解,dp[i][j][l]表示,那么我dp[i][j][l-1]只能由dp[i][j][l]转移过来,对于dp[i-1][j][l]和dp[i][j-1][l]也是同理的,转移方程是dp[i][j][l-1]=dp[i][j][l]*(j*k)/(j*k

Roll_Keyboard的博客 455

Yandex.Algorithm 2011 Round 2 D - Powerful array (莫队算法)

题意:给你n个数,进行m个查询,每个查询有一个区间,如果1出现了cnt[1]次,2出现了cnt[2]次,3出现了cnt[3]次…..i出现cnt[i]次,那么就要求输出1∗cnt[1]2+2∗cnt[2]2+3∗cnt[3]2+...+i∗cnt[i]21*cnt[1]^2+2*cnt[2]^2+3*cnt[3]^2+...+i*cnt[i]^2思路:莫队裸题,用cnt记录下某个数字出现,这样就能o

Roll_Keyboard的博客 428

Codeforces Round #319 (Div. 2) E. Points on Plane(分块+排序)

题意:现在有1e6个点,(0= < x,y<=1e6),对他们进行排序,使得所有相邻两个点的曼哈顿距离之和小于2.5e9思路:用类似莫队那样的分块,n‾√\sqrt{n}进行分块,这样相邻x最多为(√n)\sqrt(n),一共n个x,距离和为nn‾√n\sqrt{n},对于y,每个块移动n,共n‾√\sqrt{n}个块,所以总和还是nn‾√n\sqrt{n},但是需要注意一个地方,如果就是最初始的莫

Roll_Keyboard的博客 425
上一篇: spoj PT07J Query on a tree III (主席树+dfs序)
下一篇: SPOJ FTOUR2 Free tour II (点分治+启发式合并)
Roll_Keyboard
博客等级 码龄9年 10粉丝 128原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值