当前位置: 首页 > news >正文

UVa679 Dropping Balls (满二叉树+开关灯思想)

题目链接

A number of K balls are dropped one by one from the root of a fully binary tree structure FBT. Each time the ball being dropped first visits a non-terminal node. It then keeps moving down, either follows the path of the left subtree, or follows the path of the right subtree, until it stops at one of the leaf nodes of FBT. To determine a ball’s moving direction a flag is set up in every non-terminal node with two values, either false or true. Initially, all of the flags are false. When visiting a non-terminal node if the flag’s current value at this node is false, then the ball will first switch this flag’s value, i.e., from the false to the true, and then follow the left subtree of this node to keep moving down. Otherwise, it will also switch this flag’s value, i.e., from the true to the false, but will follow the right subtree of this node to keep moving down. Furthermore, all nodes of FBT are sequentially numbered, starting at 1 with nodes on depth 1, and then those on depth 2, and so on. Nodes on any depth are numbered from left to right. For example, Fig. 1 represents a fully binary tree of maximum depth 4 with the node numbers 1, 2, 3, …, 15. Since all of the flags are initially set to be false, the first ball being dropped will switch flag’s values at node 1, node 2, and node 4 before it finally stops at position 8. The second ball being dropped will switch flag’s values at node 1, node 3, and node 6, and stop at position 12. Obviously, the third ball being dropped will switch flag’s values at node 1, node 2, and node 5 before it stops at position 10. Now consider a number of test cases where two values will be given for each test. The first value is D, the maximum depth of FBT, and the second one is I, the I-th ball being dropped. You may assume
the value of I will not exceed the total number of leaf nodes for the given FBT.
Please write a program to determine the stop position P for each test case.
For each test cases the range of two parameters D and I is as below: 2 ≤ D ≤ 20, and 1 ≤ I ≤ 524288.

Input
Contains l + 2 lines.
Line 1 l the number of test cases
Line 2 D1 I1 test case #1, two decimal numbers that are separated by one blank

Line k + 1 Dk Ik test case #k
Line l + 1 Dl Il test case #l
Line l + 2 -1 a constant ‘-1’ representing the end of the input file

Output
Contains l lines.
Line 1 the stop position P for the test case #1

Line k the stop position P for the test case #k

Line l the stop position P for the test case #l

1.刚开始模拟了一下两个深度分别为3和4的样例,然后就发现在第i层中,首先落下的2i-2次都是偶数且这2i-2中按奇偶数来分正好是把左一半右一半的偶数叶子节点逐一遍历,同理接下来的2i-2次都是奇数。然后直接写了一个规律的模拟,过了样例,交——WA。又读了一遍题,发现小球数目是任意的,而我刚开始按最多2i-1次个小球来考虑了

2.读了几遍标答,手动模拟,搞懂了。以前做过开关灯的问题,和这个确实有思想上的类似的,可以对比着想

3.想去看下大神们有没有什么更好的理解,确实有。某博客:第i个球走的路径是i-1二进制数的逆序。0代表左子树,1代表右子树。并由右向左走D-1次即可

4.大概想了一下上面的方法,果然是很神奇的规律,我们发现从0开始递增的数,对应二进制从右向左看,第一位的0、1交替周期是2,第二位的周期为4,第三位的周期为8…而且每一位都是从0开始,刚好和二叉树的每一层开关的交替周期相同!故在这个题中将0代表左子树,1代表右子树的话,刚好是依次取D-1的每一位,直到判断到最终的叶子节点上
在这里插入图片描述

标答:

#include <iostream>
using namespace std;
int main(){
    int T,d,I;
    while(scanf("%d",&T)!=EOF){
        if(T==-1) break;
        while(T--){
            scanf("%d%d",&d,&I);
            int ans=1;
            for(int i=0;i<d-1;i++){	///写位运算可大大节省时间
                if(I&1){
                    ans<<=1;
                    I=(I+1)>>1;
                }else{
                    ans=(ans<<1)+1;
                    I>>=1;
                }
            }
            printf("%d\n",ans);
        }
    }
    return 0;
}

神奇的规律:

#include <cstdio>
#include <iostream>
using namespace std;
int main(){
    int T,p,q;
    while(scanf("%d",&T)!=EOF){
        if(T==-1) break;
        while(T--){
            scanf("%d%d",&p,&q);
            int x=q-1;
            int ans=1;
            while(--p){
                if(x&1){    ///判断最后一位是否为1,也可当做奇数偶数的判断
                    ans=(ans<<1)+1;
                }else ans<<=1;
                x>>=1;
            }
            printf("%d\n",ans);
        }
    }
        return 0;
}

相关文章:

  • UVa 548 Tree(建树+DFS)
  • Android开发指南-框架主题-安全和许可
  • UVa 699 The Falling Leaves(建树+求竖直权值和)
  • Widget带来了真正的移动互联网
  • 2019 ICPC 徐州区域赛 - C <3 numbers(素数密度)
  • 2019 ICPC 徐州区域赛 - A Cat(异或性质)
  • 2019 ICPC 南昌区域赛 - C And and Pair(思维+组合数学)
  • Android开发指南-框架主题-清单文件
  • 2019 ICPC 南昌区域赛 - G Eating Plan(技巧+暴力)
  • 离职的日子
  • 2019 ICPC 南京区域赛 - A A Hard Problem(找规律)
  • 走向架构师之路---开博寄语
  • JavaWeb拦截器拦截了静态资源的解决办法
  • 职业方向的选择
  • 2019 ICPC 南京区域赛 - H Prince and Princess(博弈+思维)
  • Android Volley源码解析
  • AWS实战 - 利用IAM对S3做访问控制
  • git 常用命令
  • Javascript基础之Array数组API
  • js继承的实现方法
  • PHP的类修饰符与访问修饰符
  • Python连接Oracle
  • Vultr 教程目录
  • WePY 在小程序性能调优上做出的探究
  • WinRAR存在严重的安全漏洞影响5亿用户
  • 不用申请服务号就可以开发微信支付/支付宝/QQ钱包支付!附:直接可用的代码+demo...
  • 给初学者:JavaScript 中数组操作注意点
  • 理解IaaS, PaaS, SaaS等云模型 (Cloud Models)
  • 力扣(LeetCode)22
  • 如何优雅的使用vue+Dcloud(Hbuild)开发混合app
  • 入口文件开始,分析Vue源码实现
  • 三栏布局总结
  • 山寨一个 Promise
  • 一个JAVA程序员成长之路分享
  • ​ArcGIS Pro 如何批量删除字段
  • ​卜东波研究员:高观点下的少儿计算思维
  • (7)STL算法之交换赋值
  • (java版)排序算法----【冒泡,选择,插入,希尔,快速排序,归并排序,基数排序】超详细~~
  • (安卓)跳转应用市场APP详情页的方式
  • (八)五种元启发算法(DBO、LO、SWO、COA、LSO、KOA、GRO)求解无人机路径规划MATLAB
  • (附源码)ssm教师工作量核算统计系统 毕业设计 162307
  • (原)Matlab的svmtrain和svmclassify
  • (转) 深度模型优化性能 调参
  • (轉貼) VS2005 快捷键 (初級) (.NET) (Visual Studio)
  • .htaccess 强制https 单独排除某个目录
  • .net core 6 使用注解自动注入实例,无需构造注入 autowrite4net
  • .NET CORE使用Redis分布式锁续命(续期)问题
  • .Net Core与存储过程(一)
  • .Net MVC + EF搭建学生管理系统
  • .Net Remoting(分离服务程序实现) - Part.3
  • .NET 中的轻量级线程安全
  • .NET国产化改造探索(一)、VMware安装银河麒麟
  • .Net转Java自学之路—SpringMVC框架篇六(异常处理)
  • @ConditionalOnProperty注解使用说明
  • @PreAuthorize注解