设为首页收藏本站

安而遇随-随遇而安

 找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 2412|回复: 0

黑客游戏后续:从Goal游戏说起

[复制链接]

 成长值: 48470

发表于 2014-9-26 09:52 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?立即注册

x
<p style="margin-bottom: 10px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 1.5em;"><span style="color: rgb(38, 38, 38);"><strong>几天前看到一个简而美的黑客编程游戏,于是乎就嚼了起来~,也拿给了同事瞅瞅。我把思路理清之后写的代码就很简洁明了,但是思路没有理清楚的话,就很难写出简洁的代码。理清需求,拆分大问题为小问题,是我想传达的。不服来战~</strong></span></p><p style="margin-bottom: 10px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 1.5em;"><strong>(细则请看原文</strong><a title="" href="http://www.aeys.org/thread-1301-1-1.html" target="_blank" textvalue="http://www.aeys.org/thread-1301-1-1.html" data_ue_src="http://www.aeys.org/thread-1301-1-1.html" style="color: rgb(35, 131, 87); text-decoration: none;">http://www.aeys.org/thread-1301-1-1.html</a><strong>)</strong></p><p style="margin-top: 15px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38); font-size: 18px;"><strong></strong></span><span style="color: rgb(38, 38, 38); font-size: 18px;"><strong>一<span style="font-family: 宋体, SimSun;"></span>、初看规则</strong></span><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38); font-size: 18px;"><strong></strong></span></p><p style="margin-bottom: 15px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 1.5em;"><span style="line-height: 1.5em; font-family: 宋体, SimSun; color: rgb(0, 176, 80);"></span></p><pre class="prettyprint lang-html prettyprinted" style="padding: 8px; background-color: rgb(247, 247, 249); border: 1px solid rgb(225, 225, 232); white-space: pre-wrap; word-break: break-all; color: rgb(102, 102, 102); font-size: 13px; line-height: 24px;"><span class="pln" style="color: rgb(72, 72, 76);">1、规则就是鼓励你打破规则,要的就是你机智!
2、程序执行时,该方案要能打印出带足够多的’o’的”goal”来展示程序的功能;
3、代码g()()('al')必须出现在源代码中。
&nbsp;&nbsp;&nbsp;i.&nbsp;g()('al')不能是一个字符串文字;
&nbsp;&nbsp;&nbsp;ii.而'al'必须是字符串,或是其他语言中的等价类型,你可以用创建自己的一套语言标准方法(例如C语言必须用",Ruby可以用"或'的任意一种;
&nbsp;&nbsp;&nbsp;iii.g()('al')在你语言中必须是有效的右值(如果适用的话)
4、g()('al')也许不能输出这样一个字符串,如果真的在你的语言中不能输出一个字符串,你应该提交一个原理解释&nbsp;:为什么它不能一个打印出一个可接受字符串的方案呢!
5、你必须能够插入任意数量的()以调用,而不用修改你的方案。如果非要修改原方案那么它就是失败的。
6、噢,提醒一下g('al')必须返回”gal”。</span></pre><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="line-height: 1.5em; font-family: 宋体, SimSun; color: rgb(0, 176, 80);"></span><span style="color: rgb(0, 176, 80);">注: 看到这里,如果想自己小试身手可以先不往下看,自己先写一段可以运行的代码,再继续往下分析</span><span style="line-height: 1.5em; font-family: 宋体, SimSun; color: rgb(0, 176, 80);"></span><br></p><p style="margin-bottom: 10px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 1.5em;"><span style="font-family: arial, helvetica, sans-serif;">这个规则看起来有点复杂,先理一理规则,思考一下这个游戏到底要我们做什么。</span></p><p style="margin-bottom: 10px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 1.5em;"><span style="font-family: arial, helvetica, sans-serif;">由于游戏要求用不同的语言实现,支持()调用在不同的语言里可能是不同的东西,例如:C++可能是仿函数,可能是构造函数等。以下都用函数指代可以执行()调用的实体。</span></p><pre class="prettyprint lang-html prettyprinted" style="padding: 8px; background-color: rgb(247, 247, 249); border: 1px solid rgb(225, 225, 232); white-space: pre-wrap; word-break: break-all; color: rgb(102, 102, 102); font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun;"><span class="pln" style="color: rgb(72, 72, 76);">1、写一个名为g的函数;</span><br><span class="pln" style="color: rgb(72, 72, 76);">2、g函数要有2个重载:</span><br><span class="pln" style="color: rgb(72, 72, 76);">&nbsp;&nbsp;&nbsp;&nbsp;i.有1个参数时,返回&nbsp;g+o+参数</span><br><span class="pln" style="color: rgb(72, 72, 76);">&nbsp;&nbsp;&nbsp;&nbsp;ii.没有参数时,再返回一个类似o的函数,区别是它在带1个参数时,要加2个o</span><br><span class="pln" style="color: rgb(72, 72, 76);">&nbsp;&nbsp;&nbsp;&nbsp;iii.有1个参数时,返回&nbsp;g+参数</span><br><span class="pln" style="color: rgb(72, 72, 76);">&nbsp;&nbsp;&nbsp;&nbsp;iv.没有参数时,返回一个函数,我叫它o函数,o函数也需要2个重载</span><br><span class="pln" style="color: rgb(72, 72, 76);">3、…以此类推。</span><br></span></pre><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun; color: rgb(0, 176, 80);"></span><span style="color: rgb(0, 176, 80);">注:看到这里,如果还没有自己小试身手的想法,建议就不要浪费时间再往下看了,看了也白看</span><span style="font-family: 宋体, SimSun; color: rgb(0, 176, 80);"></span></p><p style="margin-top: 15px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38); font-size: 18px;"><strong></strong></span><span style="color: rgb(38, 38, 38); font-size: 18px;"><strong>二、小试牛刀</strong></span><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38); font-size: 18px;"><strong></strong></span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun;"></span>由于最近初学lua,lua的函数是first-class的,所以我的直觉就是lua能非常简单地解决这个问题,所以下面全是lua代码的实现。其他任何函数是first-class或者语言级支持闭包的语言,都能很容易移植或者改写。<span style="font-family: 宋体, SimSun;"></span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="color: rgb(38, 38, 38);"><strong><span style="font-family: 宋体, SimSun;"></span></strong></span><span style="color: rgb(38, 38, 38);"><strong>0×001:第一次尝试</strong></span><span style="color: rgb(38, 38, 38);"><strong><span style="font-family: 宋体, SimSun;"></span></strong></span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun;"></span>问题有点复杂,让我们把问题分为两个部分<span style="font-family: 宋体, SimSun;"></span></p><pre class="prettyprint lang-html prettyprinted" style="padding: 8px; background-color: rgb(247, 247, 249); border: 1px solid rgb(225, 225, 232); white-space: pre-wrap; word-break: break-all; color: rgb(102, 102, 102); font-size: 13px; line-height: 24px;"><span class="pln" style="color: rgb(72, 72, 76);">1、约束的规则:
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;各种古怪的调用方式
2、期望的结果:
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;生成”g”+”o”*n+”al”,例如:gal,&nbsp;goal,&nbsp;gooal等</span></pre><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="line-height: 1.5em; font-family: 宋体, SimSun;"></span>这样看来,第1个部分太难,我们尝试放着第1部分不管,只实现第2部分的要求<span style="line-height: 1.5em; font-family: 宋体, SimSun;"></span><br><span style="font-family: 宋体, SimSun;"></span></p><p style="margin-bottom: 10px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 1.5em;"><span style="font-family: 宋体, SimSun;"></span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px; text-align: center;"> 14115702557664.jpg </p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun;"></span>结果跟预期的一样,现在只需要修改n的值,就能得到n个o的goal。<span style="font-family: 宋体, SimSun;"></span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38);"><strong></strong></span><span style="color: rgb(38, 38, 38);"><strong>0×002:第二次尝试</strong></span><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38);"><strong></strong></span></p><p style="margin-bottom: 10px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 1.5em;"><span style="font-family: 宋体, SimSun;"></span>看来进展挺顺利,让我们继续往下,基于第1部分的规则,我们要写一个g函数,支持2种重载,返回不同的值(字符串/o函数),返回的o函数也是类似的,支持2种重载,返回不同的值(字符串/函数)。所以,我考虑o能不能就是g呢?先假设这是可行的,让我们来试试:</p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun;">现在分析一下2种情况的重载:</span><span style="font-family: 宋体, SimSun;"></span></p><pre class="prettyprint lang-html prettyprinted" style="padding: 8px; background-color: rgb(247, 247, 249); border: 1px solid rgb(225, 225, 232); white-space: pre-wrap; word-break: break-all; color: rgb(102, 102, 102); font-size: 13px; line-height: 24px;"><span class="pln" style="color: rgb(72, 72, 76);">1、有1个参数时,返回&nbsp;‘g’+’o’*(调用g的次数-1)+参数;
2、没有参数时,返回g自己.</span></pre><p style="margin-bottom: 10px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 1.5em;"><span style="font-family: 宋体, SimSun;"></span><br></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px; text-align: center;"><span style="font-family: 宋体, SimSun;"> 14115702578887.jpg </span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun;"></span>&nbsp;可以看到,我们用一个闭包,很容易地解决了这个问题,当每次g被无参数调用的时候,o就加上一个’o’。<span style="line-height: 1.5em; font-family: 宋体, SimSun;"></span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38);"><strong></strong></span><span style="color: rgb(38, 38, 38);"><strong>0×003:第三次尝试</strong></span><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38);"><strong></strong></span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun;"></span>上面的代码看起来好像很完美了,但是g()()()()(‘al’)不能重复调用,因为g共享了同一个o变量。但其实这很容易解决。<span style="font-family: 宋体, SimSun;"></span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px; text-align: center;"><span style="font-family: 宋体, SimSun;"> 14115702606547.jpg </span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="line-height: 1.5em; font-family: 宋体, SimSun;"></span>是的,在最后返回之前,重置一下o就行了。这就是传说中的“递归结束条件”。<span style="line-height: 1.5em; font-family: 宋体, SimSun;"></span><br></p><p style="margin-bottom: 10px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 1.5em;"><strong><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38);">0×004:第4次尝试</span></strong></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun;"></span>如果上面的代码看起来已经完全符合游戏规则,甚至符合了我们自己增加的条件(因为规则并没有要求,能够重复调用)。既然已经加了个规则,我们最后尝试一下,再加个规则,就是当g没有调用g(‘al’)时,例如:g()(),后面再调用g()()(‘al’),也应该可以正确输出gooal。<span style="font-family: 宋体, SimSun;"></span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun;"></span>为了符合这个条件,我们只能让g返回另一个函数,然后实现一个真正的闭包。<span style="font-family: 宋体, SimSun;"></span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px; text-align: center;"><span style="font-family: 宋体, SimSun;"> 14115702627406.jpg </span></p><p style="margin-top: 15px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38); font-size: 18px;"><strong></strong></span><span style="color: rgb(38, 38, 38); font-size: 18px;"><strong>三、写在最后</strong></span><span style="font-family: 宋体, SimSun; color: rgb(38, 38, 38); font-size: 18px;"><strong></strong></span></p><p style="margin-bottom: 10px; padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 1.5em;"><span style="font-family: 宋体, SimSun;"></span>至此,我觉得已经玩够了,该结束了。。不知道有没有把问题描述清楚,我想说的是,再复杂的问题,只要我们理解清楚需求,拆分成小模块去逐一击破。到最后甚至可以发现规则的漏洞,自己去加强规则,玩转规则。</p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="line-height: 1.5em; font-family: 宋体, SimSun;"></span>小编:感谢这位freebuffer的热情参与,我们期待更多<span style="line-height: 1.5em; font-family: 宋体, SimSun;">!</span></p><p style="padding-top: 6px; padding-bottom: 4px; overflow: hidden; color: rgb(102, 102, 102); font-family: 微软雅黑, 'Microsoft YaHei', 'WenQuanYi Micro Hei'; font-size: 13px; line-height: 24px;"><span style="line-height: 1.5em; color: rgb(38, 38, 38);"><strong>源地址</strong></span><a title="" href="http://jennal.com/2014/09/23/%E4%BB%8Egoal%E6%B8%B8%E6%88%8F%E8%AF%B4%E8%B5%B7/" target="_blank" data_ue_src="http://jennal.com/2014/09/23/从goal游戏说起/" style="line-height: 1.5em; color: rgb(38, 38, 38);"><strong>http://jennal.com/2014/09/23/从goal游戏说起/</strong></a><span style="line-height: 1.5em; color: rgb(38, 38, 38);"><strong>]</strong></span></p><p></p>
[发帖际遇]: admin 发帖时在路边捡到 5 SB,偷偷放进了口袋. 幸运榜 / 衰神榜
随遇而安
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

快速回复 返回顶部 返回列表