热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

【HDU5977】GardenofEden(树分治)

题干:WhenGodmadethefirstman,heputhimonabeautifulgarden,theGardenofEden.HereAdamlived

题干:

When God made the first man, he put him on a beautiful garden, the Garden of Eden. Here Adam lived with all animals. God gave Adam eternal life. But Adam was lonely in the garden, so God made Eve. When Adam was asleep one night, God took a rib from him and made Eve beside him. God said to them, “here in the Garden, you can do everything, but you cannot eat apples from the tree of knowledge.” 
One day, Satan came to the garden. He changed into a snake and went to live in the tree of knowledge. When Eve came near the tree someday, the snake called her. He gave her an apple and persuaded her to eat it. Eve took a bite, and then she took the apple to Adam. And Adam ate it, too. Finally, they were driven out by God and began a hard journey of life. 
The above is the story we are familiar with. But we imagine that Satan love knowledge more than doing bad things. In Garden of Eden, the tree of knowledge has n apples, and there are k varieties of apples on the tree. Satan wants to eat all kinds of apple to gets all kinds of knowledge.So he chooses a starting point in the tree,and starts walking along the edges of tree,and finally stops at a point in the tree(starting point and end point may be same).The same point can only be passed once.He wants to know how many different kinds of schemes he can choose to eat all kinds of apple. Two schemes are different when their starting points are different or ending points are different. 

Input

There are several cases.Process till end of input. 
For each case, the first line contains two integers n and k, denoting the number of apples on the tree and number of kinds of apple on the tree respectively. 
The second line contains n integers meaning the type of the i-th apple. Types are represented by integers between 1 and k . 
Each of the following n-1 lines contains two integers u and v,meaning there is one edge between u and v.1≤n≤50000, 1≤k≤10 

Output

For each case output your answer on a single line.

Sample Input

3 2
1 2 2
1 2
1 3

Sample Output

6

题目大意:

给定N个节点的树&#xff0c;每个节点有颜色&#xff0c;共k种颜色&#xff0c;求树上所有满足从i到j所经过的点包含了所有颜色的点对&#xff0c;(i,j)和(j,i)视为不同且i可以等于j。&#xff08;N<&#61;5e4&#xff0c;k<&#61;10&#xff09;

解题报告&#xff1a;

k&#61;10&#xff0c;考虑状态压缩&#xff0c;最多可以(1<<(10)-1)种状态&#xff0c;利用树分治保存每个点到节点的路径状态。比求路径之和等于k的点对要简单&#xff0c;因为不需要容斥&#xff0c;可以用蓝书上第一种方法去求&#xff08;按照子树顺序分别处理&#xff09;&#xff0c;但是细节还是要注意&#xff0c;比如当前的根节点别被统计多次了&#xff0c;且别忘了从根节点当其中一个端点&#xff0c;开始往下一条链的那种情况&#xff0c;其实这种情况是不需要特判的&#xff0c;只需要在做当前根节点上的所有工作之前&#xff0c;让cnt[(1<

AC代码&#xff1a;

#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#define FF first
#define SS second
#define ll long long
#define pb push_back
#define pm make_pair
using namespace std;
typedef pair PII;
const int MAX &#61; 1e5 &#43; 5;
int col[MAX],head[MAX],tot,size[MAX],n,k;
struct Node {int to,ne;
} e[MAX<<1];
bool vis[MAX];
int up,cnt[MAX],tmp[MAX];
void add(int u,int v) {e[&#43;&#43;tot].to &#61; v;e[tot].ne&#61;head[u];head[u]&#61;tot;
}
ll ans;
int rt,all,son[MAX];
//getRoot调用之前必须先rt&#61;0;
void getRoot(int cur,int fa) {size[cur]&#61;1;son[cur]&#61;0;for(int i &#61; head[cur]; ~i; i &#61; e[i].ne) {int v &#61; e[i].to;if(v &#61;&#61; fa || vis[v]) continue;getRoot(v,cur); size[cur] &#43;&#61; size[v];son[cur] &#61; max(son[cur],size[v]);}son[cur] &#61; max(son[cur],all - size[cur]);//注意这里的all指的就是当前子树的节点个数 if(son[rt] &#61;&#61; 0 || son[rt] > son[cur]) rt &#61; cur;//值小&#xff0c;则更新根节点
}
void gx(int cur,int fa) {size[cur]&#61;1;for(int i &#61; head[cur]; ~i; i &#61; e[i].ne) {int v &#61; e[i].to;if(v &#61;&#61; fa || vis[v]) continue;gx(v,cur); size[cur] &#43;&#61; size[v];}
}
void get(int cur,int fa,int sta) {tmp[sta]&#43;&#43;;
// if(sta &#61;&#61; (up-1)) ans&#43;&#43;;for(int bit &#61; 0; bit}
void cal(int cur) {for(int i &#61; 0; i// get(cur,0,1<// tmp[(1<}
void dfs(int cur) {rt&#61;0; getRoot(cur,0); cur&#61;rt; vis[cur]&#61;1; gx(cur,0);cal(cur);for(int i &#61; head[cur]; ~i; i &#61; e[i].ne) {int v &#61; e[i].to;if(vis[v]) continue;all &#61; size[v]; dfs(v); }
}
int main()
{while(~scanf("%d%d",&n,&k)) {tot&#61;0; up &#61; 1<}

 


推荐阅读
  • 51nod3221祝寿(反向建图优化)
    题目链接感觉忘记了好多东西。求有向图中其余点到一个点的最短距离可以将该图翻转后rundijkstra#include#include ... [详细]
  • 本文讨论了在Windows 8上安装gvim中插件时出现的错误加载问题。作者将EasyMotion插件放在了正确的位置,但加载时却出现了错误。作者提供了下载链接和之前放置插件的位置,并列出了出现的错误信息。 ... [详细]
  • 本文主要解析了Open judge C16H问题中涉及到的Magical Balls的快速幂和逆元算法,并给出了问题的解析和解决方法。详细介绍了问题的背景和规则,并给出了相应的算法解析和实现步骤。通过本文的解析,读者可以更好地理解和解决Open judge C16H问题中的Magical Balls部分。 ... [详细]
  • 本文介绍了Swing组件的用法,重点讲解了图标接口的定义和创建方法。图标接口用来将图标与各种组件相关联,可以是简单的绘画或使用磁盘上的GIF格式图像。文章详细介绍了图标接口的属性和绘制方法,并给出了一个菱形图标的实现示例。该示例可以配置图标的尺寸、颜色和填充状态。 ... [详细]
  • 欢乐的票圈重构之旅——RecyclerView的头尾布局增加
    项目重构的Git地址:https:github.comrazerdpFriendCircletreemain-dev项目同步更新的文集:http:www.jianshu.comno ... [详细]
  • Android系统源码分析Zygote和SystemServer启动过程详解
    本文详细解析了Android系统源码中Zygote和SystemServer的启动过程。首先介绍了系统framework层启动的内容,帮助理解四大组件的启动和管理过程。接着介绍了AMS、PMS等系统服务的作用和调用方式。然后详细分析了Zygote的启动过程,解释了Zygote在Android启动过程中的决定作用。最后通过时序图展示了整个过程。 ... [详细]
  • 重入锁(ReentrantLock)学习及实现原理
    本文介绍了重入锁(ReentrantLock)的学习及实现原理。在学习synchronized的基础上,重入锁提供了更多的灵活性和功能。文章详细介绍了重入锁的特性、使用方法和实现原理,并提供了类图和测试代码供读者参考。重入锁支持重入和公平与非公平两种实现方式,通过对比和分析,读者可以更好地理解和应用重入锁。 ... [详细]
  • 本文介绍了GregorianCalendar类的基本信息,包括它是Calendar的子类,提供了世界上大多数国家使用的标准日历系统。默认情况下,它对应格里高利日历创立时的日期,但可以通过调用setGregorianChange()方法来更改起始日期。同时,文中还提到了GregorianCalendar类为每个日历字段使用的默认值。 ... [详细]
  • 本文介绍了Codeforces Round #321 (Div. 2)比赛中的问题Kefa and Dishes,通过状压和spfa算法解决了这个问题。给定一个有向图,求在不超过m步的情况下,能获得的最大权值和。点不能重复走。文章详细介绍了问题的题意、解题思路和代码实现。 ... [详细]
  • Netty源代码分析服务器端启动ServerBootstrap初始化
    本文主要分析了Netty源代码中服务器端启动的过程,包括ServerBootstrap的初始化和相关参数的设置。通过分析NioEventLoopGroup、NioServerSocketChannel、ChannelOption.SO_BACKLOG等关键组件和选项的作用,深入理解Netty服务器端的启动过程。同时,还介绍了LoggingHandler的作用和使用方法,帮助读者更好地理解Netty源代码。 ... [详细]
  • 本文详细介绍了Android中的坐标系以及与View相关的方法。首先介绍了Android坐标系和视图坐标系的概念,并通过图示进行了解释。接着提到了View的大小可以超过手机屏幕,并且只有在手机屏幕内才能看到。最后,作者表示将在后续文章中继续探讨与View相关的内容。 ... [详细]
  • 本文介绍了SPOJ2829题目的解法及优化方法。题目要求找出满足一定条件的数列,并对结果取模。文章详细解释了解题思路和算法实现,并提出了使用FMT优化的方法。最后,对于第三个限制条件,作者给出了处理方法。文章最后给出了代码实现。 ... [详细]
  • linux进阶50——无锁CAS
    1.概念比较并交换(compareandswap,CAS),是原⼦操作的⼀种,可⽤于在多线程编程中实现不被打断的数据交换操作࿰ ... [详细]
  • 第七课主要内容:多进程多线程FIFO,LIFO,优先队列线程局部变量进程与线程的选择线程池异步IO概念及twisted案例股票数据抓取 ... [详细]
  • Educational Codeforces Round 66 (Rated for Div. 2)C. Electrification ... [详细]
author-avatar
zhouib8oevlap
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有