LOGO编程题 挑战100个随机数(答案)★★★★★
在LOGO作图窗口显示100个数字并不是太困难的事。难的是要随机地完整地填入1~100这些数字。如果随意地填写这100个数字的话,就有100!种填写方法。要知道,100!——也就是100的阶乘,是一个长达158位数的“天文数字”。就算计算机每秒钟能够填写1000000种方案的话,也需要许多亿亿亿亿年!所以就必须找到科学的计算方法,而{jd1}不是盲目地填写这些数据。
关于100阶乘的计算方法
请参考林老师编写的《LOGO语言竞赛习题集》P251
用LOGO语言计算出100阶乘的158位xx值是:
JIECHENG 100
100!
=93326215443944152681699238856266700490715968264381621468592963895217
5999932299156089414639761565182862536979208272237582511852109168640000000000
00000000000000
这是一个158位数
把题目和答案分开的好处是有利于练习时独立思考
现在提供这个问题的两个不同的解决方法。
纵观各种不同的编程方式,最为合理的思维方式必定包含以下内容:
一、{zh0}预先准备好1~100这些数字,在这些预先准备好的数字中进行随机移位操作,可以避免“重复”、“缺漏”的现象;
二、在正确地产生了100个随机数后,合理的方式应该是按某种规律填写到位,否则显示输出的工作量将会很大。
{dy}个方法:林老师编写的LOGO程序:
关于使用程序换行转接号“\”的技巧请参考:
上面的程序是按照这样的思路来解决填写100个随机数字的:
①先建立:A和:B两个数组,这两个数组都有1~100个有效存储空间。
②:A数组先全部清零,用来存放{zh1}填写的结果。:B数组预先按从小到大的顺序填入1~100这些数值。
③附带说一句:各种计算机程序设计语言所输出的“随机数”其实全部都是“伪随机数”,看似无序,其实这些数值既然是计算出来的,仍然有一定的规律,所以并非{jd1}“随机”。为了保证输出结果的“随机”性,用ITEM命令剪取当前时间的“分”、“秒”值作为随机数的“种子”。因为你在什么时间开始运行这个程序是随意的,所以这个“种子”也可以看成是“随意”的。所以这个程序输出的答案可以说是相当的“随机”的。从概率上来看,绝无两次输出相同的表格的可能。
白璧微瑕:林老师偶然发现,作为“官方”xx《说明书》的LOGO语言自带的Help系统也有多处错误。例如RERAMDOM的Help说明中建议使用
RERANDOM ((ITEM 1
TIME)*3600+(ITEM 2 TIME)*60+ITEM 3 TIME)
其实是错误的。因为每天{zd0}的秒数是86400,假如“种子”值不对,LOGO系统将提示:The procedure
RERANDOM needs a number between -32768 and 32767 as its first
input. 要求种子数值在-32768~32767之间。所以不能用小时数作为“种子”!
④FOR "I 1 100[SJ :I]命令调用SJ :I子程序100次,给这100个格子填充数据。
⑤每次“检取”数据的对象是:B数组。在每次“检取”时,:B数组中有:N个数据(刚开始时:N=100)。被“检取”数据的序号(或位置):J是随机产生的。
ASET :A :I AGET :B :J命令把:B数组中第:J号空间中的数值填充到:A数组第:I号空间里去。
简单地说,每次是随意地从:B数组中“抓”一个数据填写到:A数组中。:A数组中的数据是从1号空间开始填写,下一次接着填2号、3号、……100号。
⑥现在这一步就显得十分重要了:从:B数组中,每“抓”走一个数据后,后面的数据就要全部逐个地朝前移位(移位的同时就把已经“抓”走的数据覆盖掉了,产生出来的是新的数据链),同时还要把:B数组中的数据的有效个数:N减少1。这样就能保证下一次再“抓”的数据中{jd1}不会有已经被“抓”过的。
这样执行100次后。:A数组中就已经储存好100个随机“检取”的1~100号数据。
⑦表格是按照规律画出来的。之所以留出30×30的空格,是考虑到一个字符横向要占用7个点,显示100要占用3个数位,其余的空间留些间隔好看些。
输出的例子如下:
第二个方法:“LOGO语言爱好者”编写的程序:
林老师7月22日在博客中发表了题目后,8月4日“LOGO语言爱好者”就给林老师发来了如下的程序。
这是一个十分成功、且思路巧妙的程序。程序仅用1个数组,十分简练。程序中的方格不是整体画好的,而是待到所有随机数产生好之后,按规律画一个格子、随即顺带显示输出这个格子中的数据。其中产生100个不重复的从1~100的随机数的核心部分注解如下:
先定义:B[0]~:B[99]数组空间,并预存1~100这些数字。因为只有预存了1~100这些数据,再随机从中“抓取”才能有效保证数据绝不重复。
先预设:Z=100,即MAKE "Z 100。在整个处理循环中:Z的值从100逐步递减到1。
以下是FOR "I -1 98[ ]循环中5个步骤操作的功能:
MAKE "X (RANDOM
:Z)+:I ;产生一个随机抓取:B数组的位置
MAKE "T AGET :B
:X
;把这个位置原来数组中的值暂存:T
ASET :B :X AGET :B :I+1 ;把当前数组(第:I+1空间)存储的值放到抓取的位置
ASET :B :I+1
:T
;把暂存值:T返回存入当前数组空间中
实质上是:B数组两个空间中数据的互换
MAKE
"Z
:Z-1
;产生随机数的范围缩小1 :Z值的范围100~1
操作的最终结果是:B数组中1~100数据重新随机排序。
其实这两个程序中最为优美之处是:{zh1}所有数据都按规律自动准确地找到自己的位置显示出来。
林老师编写的程序命令是:
FOR "I 1
100[PU SETXY SE (REMAINDER :I-1 10)*30-150 \
150-(INT((:I-1)/10))*30 PD TT AGET :A
:I]
“LOGO语言爱好者”编写的程序命令是:
FOR "I 0 9[FOR "J 0 9[PU SETXY SE -150+30*:I 30*:J-150
\
FG AGET :B :Z MAKE "Z :Z+1]]
我们向热心参与讨论研究的“LOGO语言爱好者”表示敬意!
你说这个LOGO命题是不是显得十分有趣?
我们还能找到其它不同类型的编程方式吗?
……
林老师博客首页的链接:
林正山老师邮箱:
需要LOGO系统文件的可以发邮件给林老师
文件包中还包括学习LOGO语言常用表格及工具程序文件
声明:
林正山老师发表的文章,媒体、网站或出版物未经本人许可谢绝进行任何形式的删节、改编、重组及转载。
允许个人博客按原文(含图片及附注)进行完整转载,转载时敬请注明本博作者姓名、文章原始出处,并以链接形式标明来源。
《LOGO语言竞赛教程》国际标准书号书号ISBN978-7-5335-3424-0,34.1万字、414页,定价22.00元,《LOGO语言竞赛习题集》国际标准书号ISBN978-7-5335-3425-7,39.6万字、481页,定价26.00元。两本书均大32开本,封面采用250克铜版纸,四色全彩印刷,内文采用60克胶版纸,黑白印刷,福建省科技出版社出版。
凡查询购买以上两本书的,林老师不再一一回函,敬请见谅。
希望购买正版书的,请自己和福州市安泰图书城一楼源泉书店0591-87547909联系。为保证书款安全,建议外地读者使用“支付宝”等第三方转交担保付款,避免直接汇款购买。