63-小猴子下落


内存限制:64MB 时间限制:3000ms Special Judge: No
accepted:2 submit:5

题目描述:

有一颗二叉树,最大深度为D,且所有叶子的深度都相同。所有结点从左到右从上到下的编号为1,2,3,·····,2的D次方减1。在结点1处放一个小猴子,它会往下跑。每个内结点上都有一个开关,初始全部关闭,当每次有小猴子跑到一个开关上时,它的状态都会改变,当到达一个内结点时,如果开关关闭,小猴子往左走,否则往右走,直到走到叶子结点。

一些小猴子从结点1处开始往下跑,最后一个小猴儿会跑到哪里呢?

输入描述:

输入二叉树叶子的深度D,和小猴子数目I,假设I不超过整棵树的叶子个数,D<=20.最终以 0 0 结尾

输出描述:

输出第I个小猴子所在的叶子编号。

样例输入:

复制
4 2
3 4
0 0

样例输出:

12
7

分析:
  1、到达某点的猴子个数如果是奇数,那么它下一个点将会往左走,同时到达这个点的猴子个数为:(n+1)/2;
  2、到达某点的猴子个数如果是偶数,那么它下一个点将会往右走,同时到达这个点的猴子个数为:n/2;
  3、模拟 (--D)次就可以得到答案
核心代码:
 1 while(-- D)
 2 {
 3     if(T&1)
 4     {
 5         ans *= 2;
 6         T = (T+1) /  2;
 7     }
 8     else
 9     {
10         ans = ans * 2 + 1;
11         T /= 2;
12     }
13 }

C/C++代码实现(AC):

 1 #include <iostream>
 2 #include <algorithm>
 3 #include <cstring>
 4 #include <cstdio>
 5 #include <cmath>
 6 #include <stack>
 7 #include <map>
 8 #include <queue>
 9 #include <set>
10 
11 using namespace std;
12 
13 int main()
14 {
15     int D, T; // D深度, T猴子个数
16     while(scanf("%d%d", &D, &T), D || T)
17     {
18         int ans = 1;
19         while(-- D)
20         {
21             if(T & 1)
22             {
23                 T = (T+1)>>1;
24                 ans *= 2;
25             }
26             else
27             {
28                 T = T >> 1;
29                 ans = ans * 2 + 1;
30             }
31         }
32         printf("%d\n", ans);
33     }
34     return 0;
35 }

 

Aspire to inspire until I expire