对于LCA(Least Common Ancestors)这类问题,其实就是求一个树中任意两点的最近的公共父节点。
其本人对其理解,先检查两节点的深度是否为同一深度,若不为同一深度,则将深度大的节点进行往上提,使其两点的深度为一致。这仅仅只是第一步,接下来,就是要使两个节点同时往上跳,可以一个一个地往上跳,使其到达第一个使这两点合并为一点的公共父节点,也是最近父节点。但一个一个跳则数据太的话,就非常耗时,于是引入了位运算中的“<<”(其实就是以2^i的形式进行倍增式跳跃),其作用就是使两点以倍增的形式往上跳,这样比一个节点以个节点地跳要省时好多,但是就引起了以下的思考:
1,如果跳到最后,两个点都跳越界了呢.....就是跳出来该树的根节点以外呢?
2,如果以倍增的形式进行上跳,如何知道它们倍增往上跳的时候跳的他们父父父父父的父节点是哪个呢?看到网上都是定义了一个二维的int数组,如:int fa[max][max],然后用fa[i][0]表示第i个节点的父节点,fa[i][1]表示第i个节点的父节点的父节点,以此类推,然后就可以得到一个递推式:fa[i][j]=fa[fa[i][j-1]][j-1],其文字叙述就是i的第2^j个父亲 是i的第2^(j-1)个父亲的第2^(j-1)个父亲。QAQ什么鬼......
3,整张图以邻接表的形式进行建图吗?那如何建呢?想过用vector来模拟邻接表,也想过用一维数组来表示,但是,有点力不从心,关键在某博客里看到定义了一个一维的vector却TM可以用二维数组的方式来表示里面的数据.....
4,用DFS对depth[n]进行赋值的话,Emmmmmmm好吧,本人会去复习一下DFS的(其实就是对图的遍历吧).....
5,在把两个节点给弄到同一深度时,有着一串代码:
if(depth[a] < depth[b]) swap(a, b);
int c = depth[a] - depth[b];
for(int i = 0; i <= 14; i++){
if(c & (1 << i)){
a = up[a][i];
}
}
其中的if(c & (1 << i))这个判断条件不是很懂......
不知道老师怎么看待这个LCA问题.......谢谢老师QAQ