二叉树的编号 小球下落

有一颗二叉树,最大深度为D,所有叶子的深度都相同。所有结点从上到下从左到右的编号分别依次是1,2,3,4,~,(2的D次方-1)。在节点1放下一个小球,它会往下落。每个内结点都有一个状态(开或关),初始时,每个内结点都处于关闭状态,当小球经过一个内结点时,开关状态会改变。当为开状态时,小球向左落下;当为关状态时,小球向下落下,直到走到叶子结点。

输出树的深度D,和小球数量I

输出第I个小球落到的结点编号

输入样例: 

4 2

3 4

2 2

16 12345

输出样例:

12

7

3

36358

 

模拟小球的下落

#include <iostream>
#include <cstring>
using namespace std;
const int MAX_N=20;
int sw[1<<MAX_N];  //每个节点的开关
int main()
{
    int d,i,k;
    while(cin >> d >> i)
    {
        memset(sw,0,sizeof(sw));
        int MAX_K = 1 << (d-1) ;
        for(int j=0; j < i; j++)
        {
            k=1;
            while(1)
            {
                sw[k]=!sw[k];
                k =  sw[k] ? k*2 : k*2+1;
                if(k>=MAX_K) break ;
            }
        }
        cout << k << endl;
    }
    return 0;
}

当题目的i为奇数时最后一个球经过第1个结点往左走为偶数则往右走

经过结点2的球总共有(i+1)/2个如果它为奇数的话接下来会往左走偶数则往右走以此内推

经过结点3的球总共有i/2个如果它为奇数的话接下来会往左走偶数则往右走以此内推

#include <iostream>

using namespace std;

int main()
{
    int d, i;
    while(cin >> d >> i)
    {
        int k = 1;
        for(int j=0; j<d-1; j++)
        {
            if(i%2)
            {
                k = k*2;
                i=(i+1)/2;
            }
            else
            {
                k=k*2+1;
                i/=2;
            }
        }
        cout << k << endl;
    }
    return 0;
}


 

©️2020 CSDN 皮肤主题: 编程工作室 设计师: CSDN官方博客 返回首页
实付0元
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值