倍增法求LCA代码加详细注释
#include <iostream>
#include <vector>
#include <algorithm>
#define MAXN 100
//2^MAXLOG2>=最大深度
#define MAXLOG2 7
using namespace std; vector<int>G[MAXN];
int depth[MAXN];
int ancestor[MAXN][MAXLOG2]; void creat()//输入并存储树
{
int n,x,y;
cin>>n;//n条边
for(int i=;i<n;i++)
{
cin>>x>>y;
G[x].push_back(y);
G[y].push_back(x);
}
}
void dfs(int x,int father)
{
depth[x]=depth[father]+;//计算x深度
ancestor[x][]=father;
//计算x结点的2^i步祖先
for(int i=;i<MAXLOG2;i++)
//因为是dfs,所以深度小的结点的ancestor总会先算出来
//MAXLOG2太大了会怎样?因为ancestor[0][i]=0,所以不管怎样往上走都是0
ancestor[x][i]=ancestor[ancestor[x][i-]][i-];
for(int i=;i<G[x].size();i++)
if(G[x][i]!=father)dfs(G[x][i],x);
}
int lca(int x,int y)
{
if(depth[x]<depth[y])swap(x,y);
/*假设x与y深度相差z,x每次走2^i(i从最大每次循环减少1)步总能到达y的深度
证明:将z转换成二进制,再转换成十进制
则肯定等于2^i1 + 2^i2 + 2^i3 ... 形式 */
for(int i=MAXLOG2-;i>=;i--)
//如何防止走多了?走完后的深度比y还小,说明走多了,这时候我们就不走
if(depth[ancestor[x][i]]>=depth[y])x=ancestor[x][i];
if(x==y)return x;
//假设x与LCA相距L步,那么x,y都走L-1步仍然不相等,下面的循环是让x,y走L-1步
for(int i=MAXLOG2-;i>=;i--)
/*如何防止走多了?
注意循环结束条件,并非当x,y走完后相等
如果以x,y相等为结束条件,则有可能会走过了
此循环的目的是为了让x,y走L-1步
LCA相当于x,y的中点
为什么一定刚好走L-1步?
首先能确定的是存在两个结点再往上一步就是LCA
此循环让x,y只要不相等就往上走,x,y肯定会到达这两个结点
即x,y走L-1步会到达那两个结点。自己可以画图试试*/
if(ancestor[x][i]!=ancestor[y][i])
{
x=ancestor[x][i];
y=ancestor[y][i];
}
return ancestor[x][]; //即x再向上走1(2^0)步即是LCA
}
int main()
{
creat();//数据要输入
dfs(,);
//cout<<lca(7,6);
return ;
}
倍增法求LCA代码加详细注释的更多相关文章
- 倍增法求lca(最近公共祖先)
倍增法求lca(最近公共祖先) 基本上每篇博客都会有参考文章,一是弥补不足,二是这本身也是我学习过程中找到的觉得好的资料 思路: 大致上算法的思路是这样发展来的. 想到求两个结点的最小公共祖先,我们可 ...
- 倍增法求LCA
倍增法求LCA LCA(Least Common Ancestors)的意思是最近公共祖先,即在一棵树中,找出两节点最近的公共祖先. 倍增法是通过一个数组来实现直接找到一个节点的某个祖先,这样我们就可 ...
- HDU 2586 倍增法求lca
How far away ? Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)To ...
- 倍增法求LCA(最近公共最先)
对于有根树T的两个结点u.v,最近公共祖先x=LCA(u,v)表示一个结点x,满足x是u.v的祖先且x的深度尽可能大. 如图,根据定义可以看出14和15的最近公共祖先是10, 15和16的最近公共 ...
- 树上倍增法求LCA
我们找的是任意两个结点的最近公共祖先, 那么我们可以考虑这么两种种情况: 1.两结点的深度相同. 2.两结点深度不同. 第一步都要转化为情况1,这种可处理的情况. 先不考虑其他, 我们思考这么一个问题 ...
- 在线倍增法求LCA专题
1.cojs 186. [USACO Oct08] 牧场旅行 ★★ 输入文件:pwalk.in 输出文件:pwalk.out 简单对比时间限制:1 s 内存限制:128 MB n个被自 ...
- 倍增法求lca:暗的连锁
https://loj.ac/problem/10131 #include<bits/stdc++.h> using namespace std; struct node{ int to, ...
- 浅谈倍增法求解LCA
Luogu P3379 最近公共祖先 原题展现 题目描述 如题,给定一棵有根多叉树,请求出指定两个点直接最近的公共祖先. 输入格式 第一行包含三个正整数 \(N,M,S\),分别表示树的结点个数.询问 ...
- 51nod 1126 求递推序列的第N项 思路:递推模拟,求循环节。详细注释
题目: 看起来比较难,范围10^9 O(n)都过不了,但是仅仅是看起来.(虽然我WA了7次 TLE了3次,被自己蠢哭) 我们观察到 0 <= f[i] <= 6 就简单了,就像小学初中学的 ...
随机推荐
- SpringCloud Netflix (五) : Hystrix 服务熔断和服务降级
什么是Hystrix 在分布式环境中,许多服务依赖项中的一些服务依赖不可避免地会失败.Hystrix是一个库,通过添加延迟容忍和容错逻辑,帮助您控制这些分布式服务之间的交互.Hystrix通过隔离服务 ...
- 使用python对oracle进行简单性能测试
一.概述 dba在工作中避不开的两个问题,sql使用绑定变量到底会有多少的性能提升?数据库的审计功能如果打开对数据库的性能会产生多大的影响?最近恰好都碰到了,索性做个实验. sql使用绑定变量对性能的 ...
- HTML5面试题
1. sessionStorage和localStorage的区别 答案: sessionStorage用于本地存储一个会话(session)中的数据,这些数据只有在同一个会话中的页面才能访问并且当会 ...
- Django之form表单常用字段与插件
from django.shortcuts import render,HttpResponse from django import forms from app01 import models f ...
- Django操作cookie实例
cookie项目文件: templates模板: login.html {% load static %} <!DOCTYPE html> <html lang="en& ...
- Java——倒序输出Map集合
package com.java.test.a; import java.util.ArrayList; import java.util.LinkedHashMap; import java.uti ...
- 新来的老大,剑走偏锋,干掉AOP做操作日志,实现后我们都惊呆了
前言 用户在操作我们系统的过程中,针对一些重要的业务数据进行增删改查的时候,我们希望记录一下用户的操作行为,以便发生问题时能及时的找到依据,这种日志就是业务系统的操作日志. 本篇我们来探讨下常见操作日 ...
- Spring_Bean的配置方式
1.通过工厂方法配置bean beans-factory.xml <?xml version="1.0" encoding="UTF-8"?> &l ...
- 我的第一个jQuery插件开发(日期选择器,datePicker),功能还不完善,但用于学习参考已经足够了。
一.学习jQuery插件开发网上的帖子很多,插件开发的方式也有好几种,现在推荐一个帖子讲述的特别好,我也是这篇文张的基础上学习的. 参考:http://www.cnblogs.com/ajianbey ...
- Rocket - interrupts - Xbar
https://mp.weixin.qq.com/s/icPGf4KdSOudwuNpLxdo7w 简单介绍Xbar的实现. 1. 简单介绍 IntXbar主要用于把上游多个中断源的中断组合在一起,然 ...