《浴缸里的惊叹》 顾森-azw3,mobi,epub,txt,pdf电子书免费下载

由于链接总是被和谐,需要本书电子版的朋友关注公众号:日读1页书(ID:rdyys88),首页回复:247,或者书名,自动弹出下载地址。

副标题: 256道让你恍然大悟的趣题

作者: 顾森

内容简介:

《浴缸里的惊叹》是一本趣题集,里面的题目全部来自于作者顾森十余年来的精心收集,包括几何、组合、行程、数字、概率、逻辑、博弈、策略等诸多类别,其中既有小学奥数当中的经典题目,又有世界级的著名难题,但它们无一例外都是作者心目中的“好题”:题目本身简单而不容易,答案出人意料却又在情理之中,解法优雅精巧令人拍案叫绝。作者还有意设置了语言和情境两个类别的问题,希望让完全没有数学背景的读者也能体会到解题的乐趣。

试读

“策略问题”只是一个通俗的说法,“算法问题”才是一个更加恰当的说法。中学时苦苦钻研信息学竞赛,注定将是我人生最难忘的经历之一。在那段时间里,我第一次听说了“算法”这个词,并且有机会接触了大量经典的算法问题。我从中选择了32个自认为最漂亮的问题,希望能让大家体会到算法的魅力。

  1. 将一个人的眼睛蒙上,然后在他前面的桌子上摆放52张扑克牌,并告诉他里面恰好有10张牌是正面朝上的。要求他把所有牌分成两堆,使得这两堆牌里正面朝上的牌的张数一样多。他应该怎么做?

首先把扑克牌分成两堆,一堆10张,一堆42张。当然,那10张正面朝上的牌并不见得正好都在小的那一堆里,不过很容易看出,小的那一堆里有多少背面朝上的,大的那一堆里就会有多少正面朝上的。因此,最后只需把小的那一堆里的所有牌全部翻过来,目的就达成了。

  1. 某种药方要求非常严格,你每天需要同时服用A、B两种药片各一粒,不能多也不能少。这种药非常贵,你不希望有任何一点的浪费。一天,你打开装药片A的药瓶,倒出一粒药片放在手心;然后打开另一个药瓶,但不小心倒出了两粒药片。现在,你手心上有一粒药片A,两粒药片B,并且你无法区别哪个是A,哪个是B。你如何才能严格遵循药方服用药片,并且不能有任何的浪费?

再取出一粒药片A,也放在手心上,因而你的手心上就有两片A和两片B了。把手上的每一片药都切成两半,分成两堆摆放。现在,每一堆药片恰好包含两个半片的A和两个半片的B。一天服用其中一堆即可。

  1. A、B两人分别在两座岛上。B生病了,A有B所需要的药。C有一艘小船和一个可以上锁的箱子。C愿意在A和B之间运东西,但东西只能放在箱子里。只要箱子没被上锁,C都会偷走箱子里的东西,不管箱子里有什么。如果A和B各自有一把锁和只能开自己那把锁的钥匙,A应该如何把东西安全递交给B?

首先A把药放进箱子,用自己的锁把箱子锁上。B拿到箱子后,再在箱子上加一把自己的锁。箱子运回A后,A取下自己的锁。箱子再运到B手中时,B取下自己的锁,获得药物。

这是应用密码学中一个非常有用的技巧,它可以用于很多协议问题,比方说抛硬币问题。如果A、B两人远隔千里,他们怎样才能采用抛掷硬币的方法来解决争端?当然,A可以自己先抛掷,然后把结果告诉B,不过前提是B必须要能完全相信A才行。如果两人互相之间都不信任,我们还有办法吗?其中一种办法是,A先准备两个盒子,每个盒子里各放一张纸条,上面分别写着“正面”和“反面”。然后,A在两个盒子上各加一把锁,并把这两个盒子都寄给B。当B收到这两个盒子后,他显然没法判断出哪个盒子装着“正面”,哪个盒子装着“反面”,只好随机选择一个盒子。这个盒子里面的字就表示抛掷硬币的结果。B把这个盒子回寄给A,然后让A来公布结果。B怎么知道A是否诚实地公布了结果呢?很简单,B手里不是还有另外一个盒子吗?B可以向A索要另外一个盒子的钥匙,然后把它打开来,看看里面装的是否是另一种结果就行了。

不过,这个协议有一个巨大的漏洞:A可以在寄盒子之前,在两个盒子里都装进“正面”,然后不管B寄回来的是哪个盒子,都骗他说“你选中的是反面”。那怎么办呢?于是,刚才的递药方法就派上用场了。B选完盒子以后,在这个盒子上再加一把自己的锁,然后把盒子寄回给A。A收到盒子后,发现自己没法改动盒子里的内容,只好解开自己的锁,把盒子再寄给B。最后,B打开盒子,看到里面写的是什么,从而得出硬币抛掷的结果。B应当把这张纸条寄给A,让A知晓硬币抛掷的结果,并让A验证这张纸条确实是A当初自己写的那张;然后,A也应当把另一个盒子的钥匙寄给B,让B验证这两个盒子里的纸条确实是一张“正面”一张“反面”。

  1. 我的班上有50个学生,他们的学号分别是1, 2, 3, …, 50。一次数学考试结束后,大家都交完试卷离开了考场。我清点试卷时发现,手里竟然只有49张卷子。究竟是谁没有交卷呢?我手边没有纸和笔,我也不想把所有卷子按照学号重新排序。我希望不借助任何工具,仅仅通过依次查看每张卷子上写的学号,便能找出缺失的那个学号。我的记忆力很有限,没法记住之前到底看到过哪些学号;不过,作为一个数学老师,我拥有非常强的计算能力。我怎样才能找出没交卷的那位同学的学号?

首先算出1到50这50个数之和,它等于1275。然后从1275这个数开始,不断减去看到的学号,最后剩下的数就是缺失的那个学号。

让我们把这个问题稍稍扩展一下。如果有两个缺失的学号,我该怎么办呢?有人或许会想到,算出1到50这50个数的和,再算出1到50这50个数的积。以后每看到一个数,就从和里面减掉这个数,从积里面除掉这个数。最后我便能求出剩余两个数的和与积,就能解出这两个数各是多少了。这个方法不太可行,毕竟从1乘到50将会得到一个65位数,即使计算机也很难直接处理。更好的办法则是,算出1到50这50个数的和,再算出1到50这50个数的平方和。以后每看到一个数,就从和里面减掉这个数,从平方和里面减掉这个数的平方。最后我便能求出剩余两个数的和与平方和,就能解出这两个数各是多少了。

  1. 有一条通信线路,每次可以发送一个由数字0到9组成的任意长的数字串。怎样利用这条通信线路,让我可以一次给你发两个数字串?这意味着,我们需要商量一种用一个数字串表示两个数字串的方案。注意到,直接将两个数字串相连是不行的,因为这将会产生歧义。如果你收到的数字串是1234,你没法知道我发送的是数字串12和34,还是数字串123和4,抑或是1和234。

这是一个与数字通信、编码解码相关的问题,如果你之前从未接触过这个领域,相信你一定会觉得它非常有意思。

你的第一想法或许是,用数字0当作分隔符不就行了吗?其实,这仍然不能解决问题。对方收到10203之后,会弄不清楚这到底是1和203,还是102和3。那用00当分隔符呢?也不行,对方收到1002003之后,同样会弄不清楚这是什么意思。看来,用特殊数字当作分隔符的思路就死掉了。

能否把第一个数字串重复说一次呢?比如,把12和34编码为121234,这样我们就能提取出第一个数字串了呀?这样也不行,对方收到11112后就弄不清楚,我发的究竟是11和2,还是1和112了。

那么,能否把第一个数字串的位数编码进去,比如把12和34编码成21234,这样不就知道第一个数字串到哪儿截止了吗?还是不行,因为你不知道这个位数信息本身到哪儿截止。假如编码结果是123456789012345,你就不知道第一个数字串是1位还是12位了。

其实,解决这个问题的方法有很多。比方说,你可以考虑用00表示0,用01表示1 ,用02表示2,等等,一直到用09表示9,最后用10表示分隔符。因此,1234和5678就可以编码为010203041005060708。不过,这种编码方式的效率很低,两个4位的数字串最后竟然变成了一个18位数。有一种简单的改进方法:既然首次出现的10一定是分隔符,后一个数字串就不必再变形了,1234和5678就可以编码为01020304105678。如果和之前“写明第一个串的位数”的思路结合一下,我们还会得到一种冗余更少的编码方案:把第一个数字串的位数用这种复杂形式来表示,并以一个10来收尾,接下来依次写出两个数字串即可。因而,1234和5678就可以编码为041012345678。举个更复杂的例子吧:12345678901234567890和12345就将会编码为:

0200101234567890123456789012345

读取编码后的数字串时,如果读到的是0?0?0?…的模式,那么我们都是在读取第一个数字串的位数;什么时候模式被打破了,出现了一个10,第一个数字串的位数也就读完了。这样,我们就能没有歧义地提出第一个数字串和第二个数字串了。

除了用升位的方法避免歧义以外,我们还有很多别的方法。例如,我们可以用01表示分隔符,然后用00表示真正的0。解码时,每读到一个0,都看看它后面跟的是什么,如果还是一个0,表明这是一个真正的0;如果是1,则表明这是一个分隔符。你会发现,刚才的编码系统还能继续改进,使得编码结果可以再少几位。12345678901234567890和12345就将会编码为:

200011234567890123456789012345

“200”其实就是20的意思,表示第一个数字串有20位。接下来的“01”则代表位数标记的结束。程序员可能会发现,这个数字0的作用其实就相当于计算机编程中的“转义符”。

  1. 有一条无限向右延伸的小路,从某个位置开始,每向右走10米就会有一个洞。不妨把这些洞从左至右依次编号为1, 2, 3, …。某天半夜,有只狐狸躲进了某个洞里。接下来的每个白天,你都只允许检查一个洞(如果此时狐狸正好在这个洞里,它就被你抓住了);每个夜晚,狐狸都会跳到它右边相邻的那个洞里。你是否有办法可以保证在有限的时间里抓住狐狸?

这个问题麻烦就麻烦在,狐狸所在的位置没有一个上限。如果你始终盯着100号洞看,有可能一辈子也抓不住狐狸,因为狐狸一开始有可能就在101号洞里;如果你始终盯着1000号洞看,也有可能一辈子也抓不住狐狸,因为狐狸一开始有可能就在1001号洞里。那怎么办呢?

很简单,我们只需要按照1, 3, 5, 7, 9, 11, …的顺序依次检查这些洞就行了,换句话说第一个白天检查1号洞,第二个白天检查3号洞,第三个白天检查5号洞,以此类推。这相当于是每天依次枚举狐狸的初始位置。第一个白天,我们猜测“狐狸初始时在1号洞”,于是检查一下1号洞;第二个白天,我们猜测“狐狸初始时在2号洞”,但若真是这样,狐狸现在就已经到3号洞了,于是我们检查一下3号洞;第三个白天,我们猜测“狐狸初始时在3号洞”,但若真是这样,狐狸现在就已经到5号洞了,于是我们检查一下5号洞……不断这样下去,我们最终总会抓到狐狸。事实上,狐狸刚开始在第几号洞里,我们就会在第几天抓到它。

我们来把这个问题加强一下。如果狐狸每晚可以往右跳不止一个洞的距离呢?换句话说,不但狐狸的初始位置我们不知道,而且狐狸每晚向右跳的距离我们也不知道。它有可能每晚都会往右跳3个洞,也有可能每晚都会往右跳100个洞(但每晚往右跳的距离是固定不变的)。即使这样,问题也是有解的。

不妨用(x, y)来表示狐狸刚开始在编号为x的洞里,每晚都会往右跳y个洞。我们需要做的就是按照某种顺序枚举所有可能的(x, y)组合,使得每一种组合都会在有限次之后被检查到。有人或许会不假思索地说,这还不简单,我们先把所有x=1的情况检查一遍,再把所有x=2的情况检查一遍,再把所有x=3的情况检查一遍,以此类推,这样不行吗?仔细想想你会发现这显然不行。为了查遍所有x=1的情况,你需要依次检验(1, 1), (1, 2), (1, 3), (1, 4), …,那么(2, 1)就永远也排不上号了。

一种可行的方法则是,先考虑所有x+y=2的情况,再考虑所有x+y=3的情况,再考虑所有x+y=4的情况,以此类推。也就是说,我们把狐狸的初始位置和移动速度的组合按照如下所示的方式列成一行:

(1, 1), (1, 2), (2, 1), (1, 3), (2, 2), (3, 1), (1, 4), (2, 3), (3, 2), (4, 1), …

然后我们每天考虑一种情况,检查一下狐狸是否在它此时应该在的位置。这样便能保证,不管狐狸初始位置在那儿,向右跳的距离是多少,我们都会在有限步之后考虑到这种情况。

在对无穷集合的研究当中,上面这种“列举所有元素”的技巧将会起到非常关键的作用。

  1. 某个国王手下有8个大臣。国王定期主持国家会议,届时8个大臣将会间隔均匀地坐在圆桌上。每个座位前都有一盏照明灯,只有所有的灯都亮了,会议才能开始。如果有些灯没亮,国王就会下达指令,让指定位置上的大臣按下座位前的灯的开关,把没亮的灯都打开。不妨将座位从1到8顺序编号,假设其中编号为2、3、7的座位前没有亮灯。于是,国王下令这3个位置上的大臣按下各自面前的开关,把这3盏灯打开,这样才能开始会议议程。

在这8个大臣中,有一个奸臣。这次会议的议题恰好就是商讨惩治这个奸臣的办法。奸臣知道自己难逃一劫,但他希望能够无限制地拖延会议。他可以在所有大臣就座前精心设置各个照明灯的初始状态,并在国王每次下达指令之后(但在大臣执行命令之前)把圆桌旋转到一个合适的位置,让大臣们按下错误的开关。

注意,在会议结束前,奸臣仍然是8个大臣中的一员。国王每次只能列出一个或多个1到8之间的数,然后下令“座位编号在此列表当中的大臣改变各自面前的灯的状态”。奸臣可以任意旋转圆桌,改变灯与大臣的对应关系。当然,他也可以选择不旋转圆桌。即使桌子被旋转过,所有大臣也必须严格遵守国王的指令。

奸臣可以始终保证灯不会全亮,从而无限制地拖延会议吗?

奸臣是无法得逞的。不管奸臣怎样设定初始局面,如何旋转桌子,国王都能精心地下达命令,使得最终所有灯都亮。不妨让我们先从简单的例子开始。

如果大臣一共只有2个,国王肯定是必胜的。如果这2盏灯都是亮的,国王就已经获胜了;如果这2盏灯都是灭的,国王只需要下令所有大臣同时按下开关,也能立即获胜。也就是说,只要初始时2盏灯的状态是相同的,国王就能保证取胜了。如果初始时2盏灯的状态不同呢?国王可以随便叫某个人按下开关。不管奸臣是否旋转圆桌,2盏灯的状态都会变得相同,国王最迟可在下一轮获胜。

如果大臣一共有4个,国王也能获胜。首先,把每两个相对位置上的灯视为一组,这样我们就把4盏灯分成了2组。把这2组灯看作是2个“超级灯”。如果一组灯里的两个灯泡状态相同,我们就认为这盏超级灯发亮;如果这组灯里的两个灯泡状态不同,就认为这盏超级灯不亮。接下来,国王只对编号为1、2的座位下达命令,那么不管奸臣怎么旋转圆桌,每组灯里最多也只有一个灯泡改变状态。事实上,我们完全可以把现在的情形等价地想象成:

(1) 圆桌旁有4个座位,有2个大臣坐在圆桌的其中半边;

(2) 桌上有2盏超级灯,旋转圆桌半周正好让这2盏超级灯重新回到初始位置;

(3) 这2个大臣面前各有一个开关,作用就是反转他面前的超级灯的状态。

大家会发现,这本质上与只有2个大臣的情况没有任何区别。刚才说了,对于只有2个大臣的情况,国王是必胜的,因此现在,国王可以套用这个策略,让每一盏超级灯都发亮。换句话说,国王能够让位于对称位置上的每一组灯都处于相同的状态。

接下来,国王把每两个处于对称位置的座位也编为一组,于是这4个座位就被分成了(1, 3)和(2, 4)这2组。此后,国王总是成组地下达指令,叫某个人按下开关,必须要叫和他同组的另一个人也按下开关。这下,不管奸臣怎么旋转圆桌,每组灯里的灯泡状态要么同时改变,要么都不变,于是每组灯里两个灯泡的状态都继续保持相同。重新解释超级灯的状态:如果这组灯的两个灯泡都亮,就认为这盏超级灯是亮的;如果这组灯的两个灯泡都不亮,则认为这盏超级灯不亮。容易看出,这下又成了这样的情况:桌子上有2盏超级灯,分别由2组人来控制,奸臣可以旋转桌子,改变2盏超级灯与2个小组之间的对应关系。因此,国王再次套用2盏灯时的策略,便能让所有超级灯都发亮。这样,所有4个灯泡就全亮了。

好了,国王已经能对付4个大臣的情况了。实际上,我们一共有8个大臣,怎么办呢?类似地,我们把每两个关于圆桌中心对称的灯看作一组,形成4盏超级灯,然后利用只有4个大臣时的解法,把这4盏超级灯都点亮。这样,每两个位置相对的灯都将拥有相同的状态。然后,修改超级灯的定义,并且再次利用只有4个大臣时的解法,最后把所有灯全部变亮。

大家很快便能想到,有8个大臣时的策略可以继续扩展到有16个大臣时的情形,并且还能继续扩展下去,因而我们证明了,当大臣数目为1, 2, 4, 8, 16, 32, …的情况下,国王都有必胜的策略。其他情况呢?其实,在其他情况下,奸臣都是能得逞的。

首先,当大臣的总人数是奇数时,奸臣都能必胜。奸臣只需要让初始时灯泡既不全亮也不全灭就行了(别忘了,奸臣可以在所有大臣就座前设定各个照明灯的初始状态)。如果灯泡既不全亮又不全灭,那么我们一定能找到相邻的两盏灯,它们是一亮一灭的。奸臣可以保证今后这两盏灯始终一亮一灭。如果国王对所有人都下指令,奸臣大可不必担心,这两盏灯显然仍然一亮一灭。如果国王只对一部分人下指令,那么由于总人数是奇数,因而即使国王故意间隔着选人,也将不可避免地出现两个相邻的人,他们都被叫到了或者都没被叫到。此时,奸臣旋转桌子,让那两盏灯对齐这两个人,从而保持这两盏灯仍然一亮一灭。

然后,我们来说明,只要大臣的总人数能被某个奇数整除,奸臣也是必胜的。比方说,如果大臣一共有28个,这是一个能被7整除的数,除出来的结果为4。于是,我们从某盏灯出发,每隔3盏灯选出1盏灯,从而选出间隔均等的7盏灯。调整这7盏灯的初始状态,使得它们既不全亮也不全灭。国王下达指令后,我们只关心这7盏灯所对应的人是否被叫到,并限定圆桌只能旋转4的倍数格。这样,我们便可以完全把其他灯都无视掉,对这7盏灯套用灯数为奇数时的做法,从而让这7盏灯始终不能全亮。这就足以让会议无限延期了。

所以,除非大臣人数只含有因数2,否则奸臣都是有必胜招数的。

这个问题有一个非常强大的加强版:如果国王是盲人呢?换句话说,如果国王不能看到各个灯泡的状态,他还能通过巧妙地下达指令,保证所有灯都能亮吗?注意,由于国王不能观察灯泡的状态,因而国王就没办法见机行事了。这意味着,国王必须得构造出一张既定的指令表,使得不管灯泡的初始状态是什么,不管奸臣在中间怎么捣乱,按顺序执行这些指令就一定能让所有灯都变亮。这看上去非常困难,然而出人意料的是,当大臣数目为1, 2, 4, 8, 16, 32, …时,国王仍然有必胜的策略。

我们先来看看只有2个大臣的情况。不妨假设2个大臣的编号分别为#1和#2。此时,国王只需要依次下达以下3个命令即可。

(1) #1和#2按动开关

(2) #1按动开关

(3) #1和#2按动开关

如果初始时2个灯泡都是灭的,不管奸臣怎么旋转桌子,国王都会在第1步之后获胜;如果初始时2个灯泡是一亮一灭的,不管奸臣怎么旋转桌子,国王都会在第2步或者第3步之后获胜。当然,如果初始时2个灯泡都是亮的,国王不用操作就直接获胜了。我们能不能模仿刚才的超级灯思路,把上面那个列表推广到4个大臣的情况呢?试试看吧:

(1) #1和#2按动开关

(2) #1按动开关

(3) #1和#2按动开关

(4) #1、#2、#3和#4按动开关

(5) #1和#3按动开关

(6) #1、#2、#3和#4按动开关

其中,第1步到第3步只对#1和#2下指令,目的是让每一组对称位置上的灯泡状态变得相同;第4步到第6步则对4个大臣成组地下达指令,目的是让每一组对称位置上的灯泡都变亮。但是,这个方案有一个非常严重的问题:你不知道第一阶段的目标会在哪一步实现。虽然前3步一定能实现第一阶段的目标,但对于不同的初始状态,实现目标的时刻是不一样的。对于某些初始状态,第一阶段的目标可能在第2步之后、第1步之后甚至第1步之前就已经实现了,这一阶段余下的操作反而是画蛇添足,会把已经很理想的状态破坏掉。怎么办呢?解决方法就是,在第一阶段的每个步骤后面,我们都执行一次第4步到第6步的操作!注意,由于第4步到第6步的指令都是成对下达的,因而原来每一对状态相同的灯泡将仍然保持状态相同,原来每一对状态不同的灯泡将仍然保持状态不同。因此,把第4步到第6步大量地插入到第一阶段当中,不会打乱第一阶段本来的进度。完整的命令列表如下:

(1) #1、#2、#3和#4按动开关

(2) #1和#3按动开关

(3) #1、#2、#3和#4按动开关

(4) #1和#2按动开关

(5) #1、#2、#3和#4按动开关

(6) #1和#3按动开关

(7) #1、#2、#3和#4按动开关

(8) #1按动开关

(9) #1、#2、#3和#4按动开关

(10) #1和#3按动开关

(11) #1、#2、#3和#4按动开关

(12) #1和#2按动开关

(13) #1、#2、#3和#4按动开关

(14) #1和#3按动开关

(15) #1、#2、#3和#4按动开关

这就是有4个大臣时国王的必胜策略。我们可以用类似的办法,继续把它扩展到大臣数为8, 16, 32…的情况,从而完美地解决这个问题。

下面是一个非常经典的老题目。

  1. 有1000个一模一样的瓶子,其中有999瓶是普通的水,有1瓶是毒药。任何喝下毒药的生物都会在一星期以内死亡。现在,你只有10只小白鼠和一星期的时间,如何检验出哪个瓶子里有毒药?

注意,只用数字“0”和数字“1”组成一个10位编码,这一共有210=1024种可能,这足以给每个瓶子一个唯一的编码了。比方说,我们可以给瓶子依次编码为:

0000000000

0000000001

0000000010

0000000011

0000000100

0000000101

……

1111100110

1111100111

现在,让第1只老鼠喝掉所有编码右起第1位是“1”的瓶子,让第2只老鼠喝掉所有编码右起第2位是“1”的瓶子,以此类推。一星期后,如果第1只老鼠死了,就知道毒药瓶子的编码中,右起第1位是“1” ;如果第2只老鼠没死,就知道毒药瓶子的编码中,右起第2位是“0”……每只老鼠的死活都能确定出10位编码的一位,由此便可知道毒药瓶子的编码了。

我们把这种给物体编号的方式叫做“二进制编码”(其实,我们已经在博弈问题中用过这个概念了)。和我们生活中所用的十进制编码不同,二进制编码只会用到“0”和“1”这两个数字。如果我们用二进制来数数的话,我们应该遵循“逢二进一”而不是“逢十进一”的规律。有的朋友或许已经发现,这本书的每一道题目前面,都印有该题的二进制编码,其中第一题的二进制编码是00000000,最后一题的二进制编码则正好是11111111。

十进制数:0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, …

二进制数:0, 1, 10, 11, 100, 101, 110, 111, 1000, 1001, 1010, 1011,…

当然,除了二进制编码,还有三进制、四进制等编码,而且它们也都是有用的。比方说,如果我们把原问题稍作修改,把找出毒药的期限改成两个星期(换句话说你可以做两轮实验),那么为了从1000个瓶子中找出毒药,你最少需要几只老鼠?注意,在第一轮实验中死掉的老鼠,就无法继续参与第二轮实验了。这一次,就该轮到三进制编码出场了。我们可以利用三进制编码来证明,这回只需要7只老鼠就足够了。事实上,7只老鼠足以从37=2187个瓶子中找出毒药来。首先,给这2187个瓶子进行三进制编码。