编程揭秘刘谦春晚魔术(约瑟夫环问题Josephus)

哈喽~各位过年好哇!

相信大家应该都看了春晚刘谦表演的魔术吧,大家当时有没有跟着做成功呢,其实背后的原理很简单,现在我们来逐句分析,一起探索其中的原理吧!

首先,有四张牌假设为1,2,3,4。然后撕一半,假设撕完之后的牌后为:1,2,3,4,1`,2`,3`,4`。然后有数字的牌面向下,放在一起之后,编号依次令为:4`,3`,2`,1`,4,3,2,1。

这样准备工作就做好了。接着就进入正题。

Step①:根据名字的字数依次从最上面的牌放到最下方

其实,这一步与几个字完全没任何关系,假如你是两个字,在完成这一步之后,牌序列变为:2`,1`,4,3,2,1,4`,3`;假如你是三个字,在完成这一步之后,牌序列变为:1`,4,3,2,1,4`,3`,2`如果你的名字是七个字,在完成这一步之后,牌序列变为:1,4`,3`,2`,1`,4,3,2

好了,接下来关键的一步,拿起最上面的3张牌,放进剩余牌的中间任意位置。

我先解释一下,首先3张牌的目的是为了保证拿起这3张牌之后的最上面一张牌的编号与最底下的一张牌的编号一定是对应的。假如你的名字是2个字:2`,1`,4,3,2,1,4`,3`,拿起3张牌之后剩下的牌变为3,2,1,4`,3`,可以发现3与3`是对应的。假如你的名字是3个字:1`,4,3,2,1,4`,3`,2`,2与2`也是对应的关系。同理其他序列也是满足的。
其次,这3张牌插进剩下牌的中间任意位置是为了保证不影响首尾这两张牌的对应关系,因此这里只需要将这3张牌插进中间的任意位置即可,并不会影响首尾的两张牌。

好了,在按照上述要求完成第一步之后,假设牌序列为:2,1,1`,4,3,4`,3`,2`。这样第一步就完成了。

Step②:将最上面的一张牌藏起来

此时最上面的一张牌为2,暂时藏起来。

此时牌序列变为:1,1`,4,3,4`,3`,2`。

Step③:南方人拿起1张牌,北方人拿起2张牌,不确定拿起3张牌,并将拿起来的牌插进剩下牌的中间任意位置

其实这里你不管拿起1张,2张还是3张无关竟要,然后将拿起的牌插进剩下牌的中间任意位置(小尼就是这里出现了失误,不小心把一张牌放到了最后一张牌的后面哈哈),这里插进中间任意位置的原因与Step1类似,并不会影响最后一张牌的位置。

假设我拿起3张牌,这一步之后牌的序列为:3,4`,1,1`,4,3`,2`。

Step④:男生拿起1张牌,女生拿起2张牌,并将拿起的牌扔掉

如果我拿起1张牌,并将这张牌扔掉之后,牌的序列变为:4`,1,1`,4,3`,2`;

如果我拿起2张牌,并将这2张牌扔掉之后,牌的序列变为:1,1`,4,3`,2`。

Step⑤:“见证奇迹的时刻”

完成这个操作之后,

如果你是男生,手里的牌序列应该为:1,1`,4,3`,2`,4`。

如果你是女生,手里的牌序列应该为:4,3`,2`,1,1`。

Step⑥:“好运留下来,烦恼丢出去”

好了,进入正题。这里本质就是约瑟夫环问题(Josephus)。(如果有不太了解约瑟夫环的朋友,可以看我之前写的这篇文章比较详细:约瑟夫环问题(Josephus)-CSDN博客)

为了简单起见,本篇文章用最简单的数组来模拟实现约瑟夫环问题。

如果你是男生,此时手里还剩下6张牌,序列依次为:1,1`,4,3`,2`,4`;(2`编号为5)

如果你是女生,此时手里还剩下5张牌,手里的牌序列应该为:4,3`,2`,1,1`。(2`编号为3)

现在我们先一步一步操作,来观察一下每一步剩余牌的序列:

·假设还剩6张牌(1,1`,4,3`,2`,4`)

1)1放到最后面,1`扔掉。

序列变为:4,3`,2`,4`,1。

2)4放到最后面,3`扔掉。

序列变为:2`,4`,1,4。

3)2`放到最后面,4`扔掉。

序列变为:1,4,2`。

4)1放到最后面,4扔掉。

序列变为:2`,1。

5)2`放到最后面,1扔掉。

序列变为:2`。

扔掉牌的序列依次为:1`,3`,4`,4,1。

·假设还剩5张牌(4,3`,2`,1,1`)

1)4放到最后面,3`扔掉。

序列变为:2`,1,1`,4。

2)2`放到最后面,1扔掉。

序列变为:1`,4,2`。

3)1`放到最后面,4扔掉。

序列变为:2`,1`。

4)2`放到最后面,1`扔掉。

序列变为:2`。

扔掉牌的序列依次为:3`,1,4,1`。

通过上面逐步分析,可以发现无论你最后还剩6张牌还是5张牌,出局序列都是约瑟夫环的淘汰序列。

注意看我紫色标记的数字以及对应的下标位置(假设编号从1开始),此时其他位置的牌是什么数字已经无所谓了,可以理解为只是一个名字代号而已。现在只需要关心接下来约瑟夫环的淘汰顺序即可。


如果此时手里还剩下6张牌,转化为约瑟夫环问题,这里就相当于总人数为6,从编号为1的人开始从“1”报数,报数为“2”的人出局。

代码如下:

Code1:

#include<iostream>
#define n 6     // 总人数
#define m 2     // 出局数字
#define k 1     // 第k个人开始报数
using namespace std;int main()
{int a[n+1];int i;int count=0; // 报数int out_count=0; // 出圈人数数量for(i=1;i<=n;i++)a[i]=i;       // 给每个人编号 1~N (即将数组 a[1]~a[N] 分别赋值为 1~N) i=k; // 第i个开始报数cout<<"最后出队序列编号为:";while(out_count!=n){if(a[i]!=0) // 编号为 0 直接跳过 {count++;if(count==m){cout<<a[i]<<' '; a[i]=0; // 出圈记为 0  out_count++; // 出圈人数数量 +1 count=0; // 每出圈一个人重新计数 }}i++;if(i==n+1) // 若 i 超过数组最大下标,则 i 从第一个下标重新开始 i=1; }cout<<endl; 
}  

代码运行结果为:

通过运行结果可以发现:

出局的编号依次为2,4,6,3,1,5,所对应的牌依次为:1`,3`,4`,4,1,2`,可以发现最后剩下的1张牌2`与Step②藏的2正好对应了起来。

如果此时手里还剩下5张牌,转化为约瑟夫环问题,这里就相当于总人数为5,从编号为1的人开始从“1”报数,报数为“2”的人出局。

代码如下:(只需将宏定义的n改为5即可)

Code2:

#include<iostream>
#define n 5     // 总人数
#define m 2     // 出局数字
#define k 1     // 第k个人开始报数
using namespace std;int main()
{int a[n+1];int i;int count=0; // 报数int out_count=0; // 出圈人数数量for(i=1;i<=n;i++)a[i]=i;       // 给每个人编号 1~N (即将数组 a[1]~a[N] 分别赋值为 1~N) i=k; // 第i个开始报数cout<<"最后出队序列编号为:";while(out_count!=n){if(a[i]!=0) // 编号为 0 直接跳过 {count++;if(count==m){cout<<a[i]<<' '; a[i]=0; // 出圈记为 0  out_count++; // 出圈人数数量 +1 count=0; // 每出圈一个人重新计数 }}i++;if(i==n+1) // 若 i 超过数组最大下标,则 i 从第一个下标重新开始 i=1; }cout<<endl; 
}  

运行结果如下:

通过运行结果可以发现:

出局的编号依次为2,4,1,5,3,所对应的牌依次为:3`,1,4,1`,2`,可以发现最后剩下的1张牌2`与Step②藏的2正好对应了起来。

这样我们就成功地梳理了一遍魔术的流程,并且用C语言验证了结果。

你们理解其中的原理了吗?

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://xiahunao.cn/news/2779253.html

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

【Rust】——猜数游戏

&#x1f383;个人专栏&#xff1a; &#x1f42c; 算法设计与分析&#xff1a;算法设计与分析_IT闫的博客-CSDN博客 &#x1f433;Java基础&#xff1a;Java基础_IT闫的博客-CSDN博客 &#x1f40b;c语言&#xff1a;c语言_IT闫的博客-CSDN博客 &#x1f41f;MySQL&#xff1a…

MySQL篇----第十七篇

系列文章目录 文章目录 系列文章目录前言一、对于关系型数据库而言,索引是相当重要的概念,请回答有关索引的几个问题二、解释 MySQL 外连接、内连接与自连接的区别三、Myql 中的事务回滚机制概述前言 前些天发现了一个巨牛的人工智能学习网站,通俗易懂,风趣幽默,忍不住分…

redis之布隆过滤

目录 1、redis之布隆过滤 2、布隆过滤器原理 3、布隆过滤器使用步骤 初始化bitmap 添加占坑位 判断是否存在圜 1、redis之布隆过滤 布隆过滤&#xff1a;有一个初值都为0的bit数组和多个哈希函数构成&#xff0c;用来快速判断集合中是否存在某个元素。目的&#xff1a;减…

顶级思维方式——认知篇三(财富与金钱)

目录 1、 什么是财富/财富的定义&#xff1f; 2、财富的影响 3、 财富意味着什么&#xff1f; 4、财富与幸福的关系 5、物质财富如何使用才有实际意义&#xff1f; 6、金钱的运作方式 7、【物质财富自由】后的选择 1、 什么是财富/财富的定义&#xff1f; 财富是一个多维…

c++之说_14|左值引用与右值引用

提起左右值引用我就头疼 左值&#xff1a; 1、在内存中开辟了空间的便叫左值 2、左值不一定可以赋值 如字符串常量 3、左值可以取地址 右值&#xff1a; 1、在内存中没有开辟空间的 2、右值无法取地址 如&#xff1a; 立即数&#xff08;1&#xff0c;2&#xff0c;3…

移动端web开发布局

目录 flex布局&#xff1a; flex布局父项常见属性&#xff1a; flex布局子项常见属性&#xff1a; REM适配布局&#xff1a; 响应式布局&#xff1a; flex布局&#xff1a; 需要先给父类盒子设置display&#xff1a;flex flex是flexiblebox的缩写&#xff0c;意为"弹…

面试经典150题——三数之和

​"The road to success and the road to failure are almost exactly the same." - Colin R. Davis 1. 题目描述 2. 题目分析与解析 2.1 思路一——暴力方法 因为三个数相加为0&#xff0c;那么说明其中两个加数的和与另一个加数为相反数则满足题意。所以可以得到…

猫头虎分享已解决Bug || IndexError: index 3 is out of bounds for axis 0 with size 3

博主猫头虎的技术世界 &#x1f31f; 欢迎来到猫头虎的博客 — 探索技术的无限可能&#xff01; 专栏链接&#xff1a; &#x1f517; 精选专栏&#xff1a; 《面试题大全》 — 面试准备的宝典&#xff01;《IDEA开发秘籍》 — 提升你的IDEA技能&#xff01;《100天精通鸿蒙》 …

解决挂梯子 无法正常上网 的问题

方法&#xff1a; 打开 控制面板 &#x1f449; 网络和Internet &#x1f449; Internet选项 &#x1f449; 连接 &#x1f449; 局域网设置 &#x1f449; 代理服务器 &#x1f449; 取消选项 有问题可参考下图

案例:三台主机实现 级联复制

介绍&#xff1a;级联复制架构 级联复制架构 是一种特殊的主从结构&#xff0c;之前聊到的几种主从结构都只有两层&#xff0c;但级联复制架构中会有三层&#xff0c;关系如下&#xff1a; 也就是在级联复制架构中&#xff0c;存在两层从库&#xff0c;这实际上属于一主多从架…

Failed to construct ‘RTCIceCandidate‘ sdpMid and sdpMLineIndex are both null

最近在搞webrtc&#xff0c;在编写函数处理远端传递来的candidate时报错了&#xff0c;具体信息如下。国内关于webrtc的资料很少&#xff0c;所以去国外社区转了一圈&#xff0c;回来记录一下报错的解决方案 其实这个bug也好解决&#xff0c;根据报错信息可以判断是RTCIceCand…

C语言第二十二弹---指针(六)

✨个人主页&#xff1a; 熬夜学编程的小林 &#x1f497;系列专栏&#xff1a; 【C语言详解】 【数据结构详解】 指针 1. 回调函数是什么&#xff1f; 2、qsort使用举例 2.1、使用qsort函数排序整型数据 2.2 使用qsort排序结构体数据 3、qsort函数的模拟实现 总结 1. 回…

龙年,大吉

&#xff08;1&#xff09; 没有成功的企业&#xff0c;只有时代的企业。这就是人们老说的&#xff1a;天道酬勤。虽然这句话被人说滥了&#xff0c;虽然这句话被人说到反感了&#xff0c;但事实就是这样。 得道者多助。 &#xff08;2&#xff09; 人有三大运、三小运。 三大运…

Python基础语法(内置Python, pycharm配置方式)

一.工具安装与配置 1.Python解释器的安装 官网网址:https://www.python.org/ 选择downloads即可(Windows用户点击Windows, 苹果用户点击macOS) 找到最新版本, 并选择 Download Windows installer (64-bit) 下载完成后可在得到一个安装包进行安装(安装时间较长) 安装完成后…

【JMX】JAVA监控的基石

目录 1.概述 2.MBean 2.1.Standard MBean 2.2.Dynamic MBean 2.3.Model Bean 2.4.Dynamic MBean和Model Bean的区别 2.5.MXBean 2.6.Open Bean 3.控制台 1.概述 什么是JMX&#xff0c;首先来看一段对话&#xff1a; Java Management Extensions&#xff08;JMX&#…

【Wio Terminal教程】使用LCD屏幕(4)

使用LCD屏幕&#xff08;4&#xff09; 一、TFT LCD的API例子1、实用图形2、数据显示3、字体4、作为背景显示 二、如何在Wio Terminal上使用LVGL图形库1、安装Seeed_Arduino_LvGL2、示例1. Bench Mark2. Stress Test3.资源 一、TFT LCD的API例子 本节为TFT LCD库的例子提供了一…

ERROR: Could not build wheels for roslz4

Python bugs 最近在安装python的rosbag包时出现了诸多问题&#xff0c;特别记录下。 python版本&#xff1a;3.11 系统版本&#xff1a;Windows10 x86_64 使用conda虚拟环境进行包管理。 运行命令 pip3 install roslz4 --extra-index-url https://rospypi.github.io/simple…

【数据结构与算法】【小白也能学的数据结构与算法】递归 分治 迭代 动态规划 无从下手?一文通!!!

&#x1f389;&#x1f389;欢迎光临&#x1f389;&#x1f389; &#x1f3c5;我是苏泽&#xff0c;一位对技术充满热情的探索者和分享者。&#x1f680;&#x1f680; &#x1f31f;特别推荐给大家我的最新专栏《数据结构与算法&#xff1a;初学者入门指南》&#x1f4d8;&am…

|Python新手小白低级教程之项目篇——turtle库|第一章:turtle库基础(1)

项目篇—文章目录 一、预告二、turtle基础1.导入2.画图代码&#xff08;1&#xff09;turtle.forward(长度)练习1.1 画线段 &#xff08;2&#xff09;turtle.left()和turtle.right()操作符练习2.1 画出边长为100正方形练习2.2 画出边长为100的三角形 &#xff08;3&#xff09…

腾讯云4核8G12M轻量应用服务器性能够用吗?支持多少人?

腾讯云轻量4核8G12M轻量应用服务器支持多少人同时在线&#xff1f;通用型-4核8G-180G-2000G&#xff0c;2000GB月流量&#xff0c;系统盘为180GB SSD盘&#xff0c;12M公网带宽&#xff0c;下载速度峰值为1536KB/s&#xff0c;即1.5M/秒&#xff0c;假设网站内页平均大小为60KB…