trie--- POJ 3764 The xor-longest Path
| Time Limit: 2000MS | Memory Limit: 65536K | |
| Total Submissions: 5453 | Accepted: 1190 |
Description
In an edge-weighted tree, the xor-length of a path p is defined as the xor sum of the weights of edges on p:
⊕ is the xor operator.
We say a path the xor-longest path if it has the largest xor-length. Given an edge-weighted tree with n nodes, can you find the xor-longest path?
Input
The input contains several test cases. The first line of each test case contains an integer n(1<=n<=100000), The following n-1 lines each contains three integers u(0 <= u < n),v(0 <= v < n),w(0 <= w < 2^31), which means there is an edge between node u and v of length w.
Output
Sample Input
4
0 1 3
1 2 4
1 3 6
Sample Output
7
Hint
The xor-longest path is 0->1->2, which has length 7 (=3 ⊕ 4)
这道题要求最长的异或路径:就是在树中找两个节点,两个节点间有唯一路径(因为是树),把路径不断做异或,异或完后求最大的。数据是10万,O(n2)算法超时
题目描述:
给你一棵树,n个节点(n = 100000),n-1条边每条边i都有一个权值wi。
定义任意两点间的权值为:
这两点间的路径上的所有边的值的异或。
比如a点和b点间有i,j,k三条边,那么ab两点间的权值为:wi^wj^wk
求这个最大的权值。
/*基本思路:1.因为有(x^z)^(y^z)==x^y,s所以为了求树上任意两点间的x^y的和,我们可以把从根节点开始到每个点的^值存下来(dfs解决,复杂度 O(n)),然后问题就转变为了从这些数中取出两个数字,使他们的异或值最大
如何在剩下的值中寻找两个数的异或和最大,朴素算法n^2,明显是超时的,---经典解决方法:trie树,边建树的同时边搜索匹配,因为是借助trie比较,复杂度就变为了O(nlogn),就可以过了*/
#include<iostream>
using namespace std;
#include<cstdio>
#include<cstring>
#define N 100010
struct Edge{/*边表*/
int v,w,last;
}edge[*N];
int head[N]={},t=;
struct Trie{
int next[];
}trie[N<<];/*trie树*/
bool visit[N]={false};
int n,ans=;
int value[N]={},topt=;/*value数组各结点到结点0的异或长度*/
void add_edge(int u,int v,int w)
{
++t;
edge[t].v=v; edge[t].w=w;
edge[t].last=head[u];
head[u]=t;
}
void dfs(int k,int val)
{
visit[k]=true;
value[k]=val;/*dfs求value数组的过程*/
for(int l=head[k];l;l=edge[l].last)
{
if(!visit[edge[l].v])
dfs(edge[l].v,val^edge[l].w);
}
} void add_trie(int num)
{
int now=;/*建trie树的过程*/
for(int i=;i>=;--i)
{
int a=num&(<<i)?:;/*取出num的二进制位的快速方法,注意这里最好用三目运算符解决,我直接用a=num&(1<<i),虽然结果正确,但是在网上提交总是runtime error*/
if(!trie[now].next[a])
trie[now].next[a]=++topt;
now=trie[now].next[a];
}
}
int find(int num)/*从二进制的第31位到第1位查找最大异或值*/
{
int w=;
int now=;
for(int i=;i>=;--i)
{
int a=(num&(<<i))?:;/*获取num的二进制数的第i+1位上的数字的非,这样取出异或值才是最大*/
if(trie[now].next[a])
{
w|=(<<i);
now=trie[now].next[a];
}
else now=trie[now].next[!a]; }
return w;
}
int main()
{
while(scanf("%d",&n)==)
{
int u,v,w;
for(int i=;i<n;++i)
{
scanf("%d%d%d",&u,&v,&w);
add_edge(u,v,w);/*对于每个无向图中,每个节点只走一次,不能只建一条有向边,而是应该建两条边,给每一个节点做一个visit数组即可*/
add_edge(v,u,w);
}
dfs(,);
for(int i=;i<=n-;++i)
{
add_trie(value[i]);/*一边建树*/
int w=;
w=find(value[i]);/*一边查询*/
ans=max(w,ans);
}
printf("%d\n",ans);
memset(head,,sizeof(head));/*对于有多组测试数据的题目,不要忘记每次循环,把所有的量都初始化*/
memset(value,,sizeof(value));
memset(trie,,sizeof(trie));
memset(edge,,sizeof(edge));
memset(visit,,sizeof(visit));
topt=;t=;ans=;n=;
}
return ;
}
trie--- POJ 3764 The xor-longest Path的更多相关文章
- poj3764 The XOR Longest Path【dfs】【Trie树】
The xor-longest Path Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 10038 Accepted: ...
- 【POJ 3764】 The xor-longest path
[题目链接] http://poj.org/problem?id=3764 [算法] 首先,我们用Si表示从节点i到根的路径边权异或和 那么,根据异或的性质,我们知道节点u和节点v路径上的边权异或和就 ...
- 【POJ 3764】The Xor-longest Path
题目 给定一个\(n\)个点的带权无根树,求树上异或和最大的一条路径. \(n\le 10^5\) 分析 一个简单的例子 相信大家都做过这题: 给定一个\(n\)个点的带权无根树,有\(m\)个询问, ...
- 题解 bzoj1954【Pku3764 The xor – longest Path】
做该题之前,至少要先会做这道题. 记 \(d[u]\) 表示 \(1\) 到 \(u\) 简单路径的异或和,该数组可以通过一次遍历求得. \(~\) 考虑 \(u\) 到 \(v\) 简单路径的异或和 ...
- poj 3764 The xor-longest Path(字典树)
题目链接:poj 3764 The xor-longest Path 题目大意:给定一棵树,每条边上有一个权值.找出一条路径,使得路径上权值的亦或和最大. 解题思路:dfs一遍,预处理出每一个节点到根 ...
- Solve Longest Path Problem in linear time
We know that the longest path problem for general case belongs to the NP-hard category, so there is ...
- Why longest path problem doesn't have optimal substructure?
We all know that the shortest path problem has optimal substructure. The reasoning is like below: Su ...
- Poj 3764 The xor-longest Path(Trie树+xor+贪心)
The xor-longest Path Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 6455 Accepted: 1392 ...
- poj 3764 The xor-longest Path (01 Trie)
链接:http://poj.org/problem?id=3764 题面: The xor-longest Path Time Limit: 2000MS Memory Limit: 65536K ...
- ACM学习历程—POJ 3764 The xor-longest Path(xor && 字典树 && 贪心)
题目链接:http://poj.org/problem?id=3764 题目大意是在树上求一条路径,使得xor和最大. 由于是在树上,所以两个结点之间应有唯一路径. 而xor(u, v) = xor( ...
随机推荐
- php之复制文件——php经典实例
php之复制文件——php经典实例 <?php function dirCopy($dir1,$dir2){ //判断是否目录存在 if(!file_exists($dir2) || !is_d ...
- long类型的数据转化为时间
long time = 111111111111111111111:SimpleDateFormat sdf= new SimpleDateFormat("yyyy-MM-dd HH:mm: ...
- React Native DEMO for Android
Demo1: 主要知识:navigator,fecth 地址:https://github.com/hongguangKim/ReactNativeDEMO1 Demo2: 主要知识:navigato ...
- 南邮PHP反序列化
题目如下: <?php class just4fun { var $enter; var $secret; } if (isset($_GET['pass'])) { $pass = $_GET ...
- C++显式类型转换
C++显式类型转换 (注:本文例程改编自<C++ Primer>) 关于类型转换,C++保留了C语言中的类型转换方式,并提供了4中新的类型转换方式.<Effective C++> ...
- java在图片上写字
- VMware-workstation-6.5.2-156735.exe
480HD-KPZ2X-TA56C-4YTQQ VMware 12 专业版永久许可证密钥 5A02H-AU243-TZJ49-GTC7K-3C61N
- Linux 基础——常用的Linux网络命令
一.学Linux网络命令有什么好处 网络的出现,我们的生活更方便了,处理事情的效率也越来越高,也可以看到全世界文化的差异.同时我们接受新事物的信息越来越来强,新事物的信息也越来越来多.网络对于我们尔等 ...
- Mysql修改语句的运行流程
执行修改语句前要先连接数据库,这是连接器的工作. 接下来,分析器会通过词法和语法解析知道这是一条更新语句.优化器决定要使用 ID 这个索引.然后,执行器负责具体执行,找到这一行,然后更新. Mysql ...
- 使用Unity解耦你的系统—PART4——Unity&PIAB
在前面几篇有关Unity学习的文章中,我对Unity的一些常用功能进行介绍,包括:Unity的基本知识.管理对象之间的关系.生命周期.依赖注入等,今天则是要介绍Unity的另外一个重要功能——拦截(I ...