http://acm.timus.ru/problem.aspx?space=1&num=1088
严重吐槽本题阅读理解。。。
题目
不幸 降临在俄国的土地上。恶魔掠走了Ilya的同伴Alyosha Popovich,并把他拴在魔石上,这样Alyosha就不能移动了。救出被囚禁的Alyosha是很有必要的,但是没人能做到。英雄Tsar被派去打仗了。Ilya Murometz对自己说:“我要一个人救出我的朋友Alyosha,如果他死在那了,我也一起死。”Ilya说玩就跳上它的马去找Alyosha了。
Ilya骑着它的马走到了一个石头前,但是不是他要找的那个魔石,而是一个指路石,上面写着,如果你向左走,你将得到”时间限制”,如果你向右走,你将获得”错误的答案”(这里不是很理解这段话意义何在。。)Ilya崩溃地瘫坐下来。突然一只小鸟停在他身边对他说:“你为什么沮丧呢?我的好朋友”Ilya告诉小鸟他的困难后小鸟说:“这里就是这样的:如果你向左走,1小时后你还会见到长这样的石头,知道你走到大海。是恶魔捣的鬼,他希望你在这里迷路。回去吧,Ilya,不要死在这!”然后小鸟的消失了,毕竟这里本来就没有小鸟。Ilya想了很久,但是又不希望背叛与Alyosha的友谊,他又骑上了马并继续旅程。骑着骑着骑了很久。
Ilya在一个跟第一个石头长得很像的石头旁跳下了马,又开始沮丧,而且比第一次还严重。突然他就看见了魔石(玄学。。),而且离他不远,但是他又不能离开道路,否则他就会被沼泽淹没。他看见大海离他很近,他甚至可以算出魔石离大海的距离为
D
小时的路程;他自己到大海则需要
他看见道路是通向码头的,码头用连续的整数标号。Ilya令从最开始的石头一直往右走走到的码头为1号,到1号码头前往左走走道的码头为2号,以此类推。Ilya看见离他最近的码头为
输入
输入一行6个整数:
输出
如果Ilya能到达魔石,输出”YES”,否则输出”NO”。
样例输入
1 2 3 2 6 4
样例输出
YES
题解
magic stone就是Alyosha的位置啦。
然后
D
表示到离Alyosha最近的满二叉树叶节点的距离,
以下为一大堆废话,dalao请跳过。
由于是满二叉树,所以叶节点的编号就可以表示其位置了,比如5号节点,减去1后的二进制表示法为
(4)10=(100)2 ,表示先走右儿子再走两次左儿子,即0表示左儿子,1表示右儿子。然后求LCA的层数(因为没有标号,也没有必要给标号,求LCA一般求其到根节点距离,也就是层数)也很简单,只要求两个点标号减一后的二进制表示法前几位最多有多少位相同即可。比如1和4的标号是 (0)10=(000)2;(3)10=(011)2 ,有1位相同(0),所以1号和4号的LCA为第2层(如果没有相同的为第1层,即层数为相同数字+1)。然后知道了LCA就可以算Alyosha和Ilya之间的距离了,然后就没有然后了。
#include <cstdio> #include <algorithm> using namespace std; int main() { char ans[2][4] = { "NO", "YES" }; int d, e, f, dp, ep, h, dep = 0; scanf("%d%d%d%d%d%d", &d, &e, &f, &dp, &ep, &h); for (--dp, --ep; dp != ep; dp /= 2, ep /= 2) ++dep; if (dep <= max(d, e)) // 如果LCA为两者其中之一 puts(ans[abs(d - e) <= h]); else // 否则 puts(ans[dep * 2 - d - e <= h]); return 0; }