<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>夜游长空 &#187; Ruby</title>
	<atom:link href="http://www.zhangdi.name/tag/ruby/feed" rel="self" type="application/rss+xml" />
	<link>http://www.zhangdi.name</link>
	<description>Blog of Daniel &#38; Kimi</description>
	<lastBuildDate>Wed, 13 Oct 2010 05:05:40 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.0.1</generator>
		<item>
		<title>KXShell的一个Demo</title>
		<link>http://www.zhangdi.name/2008/09/21/kxshell-demo.html</link>
		<comments>http://www.zhangdi.name/2008/09/21/kxshell-demo.html#comments</comments>
		<pubDate>Sat, 20 Sep 2008 18:19:40 +0000</pubDate>
		<dc:creator>zhangdi</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[开心网]]></category>

		<guid isPermaLink="false">http://www.zhangdi.name/?p=317</guid>
		<description><![CDATA[老婆出去玩了，我一个人在家里没事干，花了一天用Ruby写了一个开心网的Shell。目前支持“争车位”的功能。 相关文章开心网“争车位”游戏分析（纯技术）加入狗狗开心网不知道我的前世解决使用gem安装时出现mkmf找不到的问题Rails on Vim]]></description>
			<content:encoded><![CDATA[<p>老婆出去玩了，我一个人在家里没事干，花了一天用Ruby写了一个开心网的Shell。目前支持“争车位”的功能。</p>
<p style="text-align: center;"><object width="425" height="344"><param name="movie" value="http://www.youtube.com/v/gf5ZidhvNxY&#038;hl=en&#038;fs=1"></param><param name="allowFullScreen" value="true"></param><embed src="http://www.youtube.com/v/gf5ZidhvNxY&#038;hl=en&#038;fs=1" type="application/x-shockwave-flash" allowfullscreen="true" width="425" height="344"></embed></object></p>
<h3  class="related_post_title">相关文章</h3><ul class="related_post"><li><a href="http://www.zhangdi.name/2008/09/17/hack-the-parking-game-in-kaixin001.html" title="开心网“争车位”游戏分析（纯技术）">开心网“争车位”游戏分析（纯技术）</a></li><li><a href="http://www.zhangdi.name/2008/12/18/fun-with-doggie.html" title="加入狗狗">加入狗狗</a></li><li><a href="http://www.zhangdi.name/2008/09/19/kaixin001-dont-know-my-qianshi.html" title="开心网不知道我的前世">开心网不知道我的前世</a></li><li><a href="http://www.zhangdi.name/2008/09/16/fixing-no-such-file-to-load-mkmf-erro.html" title="解决使用gem安装时出现mkmf找不到的问题">解决使用gem安装时出现mkmf找不到的问题</a></li><li><a href="http://www.zhangdi.name/2008/08/26/rails-on-vim.html" title="Rails on Vim">Rails on Vim</a></li></ul>]]></content:encoded>
			<wfw:commentRss>http://www.zhangdi.name/2008/09/21/kxshell-demo.html/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>开心网“争车位”游戏分析（纯技术）</title>
		<link>http://www.zhangdi.name/2008/09/17/hack-the-parking-game-in-kaixin001.html</link>
		<comments>http://www.zhangdi.name/2008/09/17/hack-the-parking-game-in-kaixin001.html#comments</comments>
		<pubDate>Wed, 17 Sep 2008 09:40:33 +0000</pubDate>
		<dc:creator>zhangdi</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[WEB20]]></category>
		<category><![CDATA[开心网]]></category>

		<guid isPermaLink="false">http://www.zhangdi.name/?p=313</guid>
		<description><![CDATA[我认识的很多人都是开心网的用户。而这些人中，又几乎所有的人都在玩“争车位”的组建游戏。我也玩了一下，一开始觉得挺能满足人的虚荣心的，毕竟可以通过鼠标就可以买到自己梦想的车了。但是不到一星期，我就有了写一个程序，自动去玩的冲动。 最开始写了一个简单的贴条程序，也就是根据一些策略，给自己车位上的车贴条。（这就是为什么有的人会发现我早上6点多给他们的车贴条的原因，显然我是不可能6点钟起床的）后来，老婆说有一个人老贴他的条，想小小的报复他一下。我就又写了一个小程序，定期的据报那个人的车（如果在自己的车位上就直接贴条了）。这个程序没有怎么使用，老婆就说已经和平解决矛盾了。 共享一下我对于“争车位”游戏的技术分析： 首先，因为开心网登录没有使用capcha，就是经常看到的验证码机制，所以给写程序登录开心网亮了绿灯。 第二，这个游戏的算法简直太简单了，因该不能称为游戏吧，因为它的交互性很少，都是一个人自己玩（这个与从Facebook上抄袭过来的朋友买卖是鲜明的对比）。更像是一个初学级别的算法题。 第三，这个游戏前台即使使用的是Flash也没有对HTTP请求的内容进行加密。这样我就可以轻易的截取这个游戏发送的所有HTTP请求进行分析了。发现，制造类似的请求非常之简单。 介绍四个“争车位”游戏的内部机制： 在“争车位”游戏的首页，源代码中找到var v_userdata=这一行JavaScript，后面就是一个JSON格式的数据信息，包含了自己车位的信息。（比如，车位上停了什么车，谁的车，挣了多少钱，车位的ID，等等，另外还有自己车的信息）找到var g_verify=这一行，后面就是一个verify string，只要有了这个字符串，开心网就会认为对面是一个用户。 /parking/post.php是贴条的网址。只要把自己的某个车位ID以及那个验证字符串和一个置为空的下划线变量POST到这个网址。这个车位上的车就会被贴条。（当然必须是你自己的车位） /parking/usercar.php是获得好友的“争车位”数据的的网址。只要把好友的用户ID（是一串数字，并不是用户名，在任何开心网的URL里面看到uid=xxxxxxx，这个就是用户ID了）以及验证信息作为参数GET这个网址，就会得到这个好友的车位信息和所有的汽车的信息。包括，几辆车，停在哪里，等等。这个没有好友限制，任何人的信息都可以得到。（只要你能知道对方的用户ID） /parking/call.php是举报的网址。只要把指定的车位ID以及验证信息POST给这个网址，就把该车位上的车举报了。这个是有好友限制的，也就是必须是好友才能举报。 只要搞定了这4条，写程序去“争车位”就应该没有什么问题了。 最后附上一个简单的贴条程序：（用Ruby写的） http://www.zhangdi.name/UserFiles/File/kx_parking.rb 相关文章KXShell的一个Demo加入狗狗开心网不知道我的前世解决使用gem安装时出现mkmf找不到的问题Rails on Vim]]></description>
			<content:encoded><![CDATA[<p>我认识的很多人都是开心网的用户。而这些人中，又几乎所有的人都在玩“争车位”的组建游戏。我也玩了一下，一开始觉得挺能满足人的虚荣心的，毕竟可以通过鼠标就可以买到自己梦想的车了。但是不到一星期，我就有了写一个程序，自动去玩的冲动。</p>
<p>最开始写了一个简单的贴条程序，也就是根据一些策略，给自己车位上的车贴条。（这就是为什么有的人会发现我早上6点多给他们的车贴条的原因，显然我是不可能6点钟起床的）后来，老婆说有一个人老贴他的条，想小小的报复他一下。我就又写了一个小程序，定期的据报那个人的车（如果在自己的车位上就直接贴条了）。这个程序没有怎么使用，老婆就说已经和平解决矛盾了。</p>
<p>共享一下我对于“争车位”游戏的技术分析：</p>
<p>首先，因为开心网登录没有使用capcha，就是经常看到的验证码机制，所以给写程序登录开心网亮了绿灯。</p>
<p>第二，这个游戏的算法简直太简单了，因该不能称为游戏吧，因为它的交互性很少，都是一个人自己玩（这个与从Facebook上抄袭过来的朋友买卖是鲜明的对比）。更像是一个初学级别的算法题。</p>
<p>第三，这个游戏前台即使使用的是Flash也没有对HTTP请求的内容进行加密。这样我就可以轻易的截取这个游戏发送的所有HTTP请求进行分析了。发现，制造类似的请求非常之简单。</p>
<p>介绍四个“争车位”游戏的内部机制：</p>
<ol>
<li>在“争车位”游戏的首页，源代码中找到var v_userdata=这一行JavaScript，后面就是一个JSON格式的数据信息，包含了自己车位的信息。（比如，车位上停了什么车，谁的车，挣了多少钱，车位的ID，等等，另外还有自己车的信息）找到var g_verify=这一行，后面就是一个verify string，只要有了这个字符串，开心网就会认为对面是一个用户。</li>
<li>/parking/post.php是贴条的网址。只要把自己的某个车位ID以及那个验证字符串和一个置为空的下划线变量POST到这个网址。这个车位上的车就会被贴条。（当然必须是你自己的车位）</li>
<li>/parking/usercar.php是获得好友的“争车位”数据的的网址。只要把好友的用户ID（是一串数字，并不是用户名，在任何开心网的URL里面看到uid=xxxxxxx，这个就是用户ID了）以及验证信息作为参数GET这个网址，就会得到这个好友的车位信息和所有的汽车的信息。包括，几辆车，停在哪里，等等。这个没有好友限制，任何人的信息都可以得到。（只要你能知道对方的用户ID）</li>
<li>/parking/call.php是举报的网址。只要把指定的车位ID以及验证信息POST给这个网址，就把该车位上的车举报了。这个是有好友限制的，也就是必须是好友才能举报。</li>
</ol>
<p>只要搞定了这4条，写程序去“争车位”就应该没有什么问题了。</p>
<p>最后附上一个简单的贴条程序：（用Ruby写的）<br />
<a href="http://www.zhangdi.name/UserFiles/File/kx_parking.rb" target="_blank">http://www.zhangdi.name/UserFiles/File/kx_parking.rb</a></p>
<h3  class="related_post_title">相关文章</h3><ul class="related_post"><li><a href="http://www.zhangdi.name/2008/09/21/kxshell-demo.html" title="KXShell的一个Demo">KXShell的一个Demo</a></li><li><a href="http://www.zhangdi.name/2008/12/18/fun-with-doggie.html" title="加入狗狗">加入狗狗</a></li><li><a href="http://www.zhangdi.name/2008/09/19/kaixin001-dont-know-my-qianshi.html" title="开心网不知道我的前世">开心网不知道我的前世</a></li><li><a href="http://www.zhangdi.name/2008/09/16/fixing-no-such-file-to-load-mkmf-erro.html" title="解决使用gem安装时出现mkmf找不到的问题">解决使用gem安装时出现mkmf找不到的问题</a></li><li><a href="http://www.zhangdi.name/2008/08/26/rails-on-vim.html" title="Rails on Vim">Rails on Vim</a></li></ul>]]></content:encoded>
			<wfw:commentRss>http://www.zhangdi.name/2008/09/17/hack-the-parking-game-in-kaixin001.html/feed</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>解决使用gem安装时出现mkmf找不到的问题</title>
		<link>http://www.zhangdi.name/2008/09/16/fixing-no-such-file-to-load-mkmf-erro.html</link>
		<comments>http://www.zhangdi.name/2008/09/16/fixing-no-such-file-to-load-mkmf-erro.html#comments</comments>
		<pubDate>Mon, 15 Sep 2008 16:47:04 +0000</pubDate>
		<dc:creator>zhangdi</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[Ubuntu]]></category>

		<guid isPermaLink="false">http://www.zhangdi.name/?p=311</guid>
		<description><![CDATA[在Ubuntu或者Debian中，使用gem安装某些程序的时候，会出现下列错误： extconf.rb:1:in `require': no such file to load -- mkmf (LoadError) 解决方法很简单： sudo apt-get install ruby1.8-dev 相关文章KXShell的一个Demo开心网“争车位”游戏分析（纯技术）Rails on Vim彻底解决Windows蓝屏Free Ruby on Rails Book]]></description>
			<content:encoded><![CDATA[<p>在Ubuntu或者Debian中，使用gem安装某些程序的时候，会出现下列错误：</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">extconf.rb:<span style="color: #000000;">1</span>:<span style="color: #000000; font-weight: bold;">in</span> <span style="color: #000000; font-weight: bold;">`</span>require<span style="color: #ff0000;">': no such file to load -- mkmf (LoadError)</span></pre></div></div>

<p>解决方法很简单：</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;"><span style="color: #c20cb9; font-weight: bold;">sudo</span> <span style="color: #c20cb9; font-weight: bold;">apt-get</span> <span style="color: #c20cb9; font-weight: bold;">install</span> ruby1.8-dev</pre></div></div>

<h3  class="related_post_title">相关文章</h3><ul class="related_post"><li><a href="http://www.zhangdi.name/2008/09/21/kxshell-demo.html" title="KXShell的一个Demo">KXShell的一个Demo</a></li><li><a href="http://www.zhangdi.name/2008/09/17/hack-the-parking-game-in-kaixin001.html" title="开心网“争车位”游戏分析（纯技术）">开心网“争车位”游戏分析（纯技术）</a></li><li><a href="http://www.zhangdi.name/2008/08/26/rails-on-vim.html" title="Rails on Vim">Rails on Vim</a></li><li><a href="http://www.zhangdi.name/2008/04/28/get-rid-of-bsod.html" title="彻底解决Windows蓝屏">彻底解决Windows蓝屏</a></li><li><a href="http://www.zhangdi.name/2007/10/09/free-ruby-on-rails-book.html" title="Free Ruby on Rails Book">Free Ruby on Rails Book</a></li></ul>]]></content:encoded>
			<wfw:commentRss>http://www.zhangdi.name/2008/09/16/fixing-no-such-file-to-load-mkmf-erro.html/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Rails on Vim</title>
		<link>http://www.zhangdi.name/2008/08/26/rails-on-vim.html</link>
		<comments>http://www.zhangdi.name/2008/08/26/rails-on-vim.html#comments</comments>
		<pubDate>Tue, 26 Aug 2008 10:53:56 +0000</pubDate>
		<dc:creator>zhangdi</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[Rails]]></category>
		<category><![CDATA[Vim]]></category>
		<category><![CDATA[开发]]></category>

		<guid isPermaLink="false">http://www.zhangdi.name/?p=306</guid>
		<description><![CDATA[一直在非常缓慢的学习RubyOnRails。工欲善其事，必先利其器。程序员的利器之一就是编辑器。所有接触过Rails的人，都会对一个叫做TextMate的编辑器记忆深刻。但是我不是Mac用户，而TextMate又坚持不出Linux和Windows版本。想花钱用都没有机会。（当然，除非先花钱买个MacBook）这就坚定了我继续使用我自己的利器－－Vim的决心。 在Ubuntu里面配置Vim非常简单。apt-get吧。然后gem install vim-ruby吧。这样你的Vim就有了最新的对于Ruby的支持。这还不够，因为我要开发Rails应用。要让Vim懂Rails。有个非常帅的Vim插件，rails.vim。它可以让人不离开Vim把Rails的一切都搞定。比如，script/generate model xxx，只需要在Vim里面:Rgenerate model xxx。还可以帮助非常快速的在Rails项目中切换文件。功能很强大，具体看这里吧。 不过，我使用的Rails是2.1+版本，这个rails.vim有一点问题。在:Rgenerate migration xxx的时候，总是打开一个空文件，而不是自动生成的migration文件。经过研究，发现原来是Rails2.1+后，每个migration文件的前缀由原来的序号变成了一个UTC的时间字符串。而rails.vim的策略是先-p执行一下命令，然后分析生成的文件名，再真正执行命令，最后打开文件。这个逻辑对于其他的命令都OK，只有migration不行。就是因为它的命名规则中加入了UTC时间字符串。导致了第一次-p执行和第二次真正执行之间文件名不同（因为时间还是稍微有差别的，比如1秒）。 知道了问题，就可以轻松把它修正。这就是源代码的力量。 在rails.vim中搜索这句话: 1 edit `=RailsRoot().'/'.file` 替换为: 1 2 3 4 5 6 7 if target == &#34;migration&#34; let suffix = strpart&#40;file, stridx&#40;file, &#34;_&#34;&#41;&#41; let filename = system&#40;'ls '.RailsRoot&#40;&#41;.'/db/migrate/*'.suffix&#41; edit `=filename` else edit `=RailsRoot().'/'.file` endif 相关文章KXShell的一个Demo开心网“争车位”游戏分析（纯技术）解决使用gem安装时出现mkmf找不到的问题为Wordpress的评论部分加上头像Free Ruby on Rails Book]]></description>
			<content:encoded><![CDATA[<p>一直在非常缓慢的学习RubyOnRails。工欲善其事，必先利其器。程序员的利器之一就是编辑器。所有接触过Rails的人，都会对一个叫做TextMate的编辑器记忆深刻。但是我不是Mac用户，而TextMate又坚持不出Linux和Windows版本。想花钱用都没有机会。（当然，除非先花钱买个MacBook）这就坚定了我继续使用我自己的利器－－Vim的决心。</p>
<p>在Ubuntu里面配置Vim非常简单。apt-get吧。然后gem install vim-ruby吧。这样你的Vim就有了最新的对于Ruby的支持。这还不够，因为我要开发Rails应用。要让Vim懂Rails。有个非常帅的Vim插件，<a href="http://www.vim.org/scripts/script.php?script_id=1567" target="_blank">rails.vim</a>。它可以让人不离开Vim把Rails的一切都搞定。比如，script/generate model xxx，只需要在Vim里面:Rgenerate model xxx。还可以帮助非常快速的在Rails项目中切换文件。功能很强大，具体看<a href="http://rails.vim.tpope.net/" target="_blank">这里</a>吧。</p>
<p>不过，我使用的Rails是2.1+版本，这个rails.vim有一点问题。在:Rgenerate migration xxx的时候，总是打开一个空文件，而不是自动生成的migration文件。经过研究，发现原来是Rails2.1+后，每个migration文件的前缀由原来的序号变成了一个UTC的时间字符串。而rails.vim的策略是先-p执行一下命令，然后分析生成的文件名，再真正执行命令，最后打开文件。这个逻辑对于其他的命令都OK，只有migration不行。就是因为它的命名规则中加入了UTC时间字符串。导致了第一次-p执行和第二次真正执行之间文件名不同（因为时间还是稍微有差别的，比如1秒）。</p>
<p>知道了问题，就可以轻松把它修正。这就是源代码的力量。</p>
<p>在rails.vim中搜索这句话:</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
</pre></td><td class="code"><pre class="ruby" style="font-family:monospace;">edit <span style="color:#996600;">`=RailsRoot().'/'.file`</span></pre></td></tr></table></div>

<p>替换为:</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
</pre></td><td class="code"><pre class="ruby" style="font-family:monospace;"><span style="color:#9966CC; font-weight:bold;">if</span> target == <span style="color:#996600;">&quot;migration&quot;</span>
  let suffix = strpart<span style="color:#006600; font-weight:bold;">&#40;</span>file, stridx<span style="color:#006600; font-weight:bold;">&#40;</span>file, <span style="color:#996600;">&quot;_&quot;</span><span style="color:#006600; font-weight:bold;">&#41;</span><span style="color:#006600; font-weight:bold;">&#41;</span>
  let filename = <span style="color:#CC0066; font-weight:bold;">system</span><span style="color:#006600; font-weight:bold;">&#40;</span><span style="color:#996600;">'ls '</span>.<span style="color:#9900CC;">RailsRoot</span><span style="color:#006600; font-weight:bold;">&#40;</span><span style="color:#006600; font-weight:bold;">&#41;</span>.<span style="color:#996600;">'/db/migrate/*'</span>.<span style="color:#9900CC;">suffix</span><span style="color:#006600; font-weight:bold;">&#41;</span>
  edit <span style="color:#996600;">`=filename`</span>
<span style="color:#9966CC; font-weight:bold;">else</span>
  edit <span style="color:#996600;">`=RailsRoot().'/'.file`</span>
endif</pre></td></tr></table></div>

<h3  class="related_post_title">相关文章</h3><ul class="related_post"><li><a href="http://www.zhangdi.name/2008/09/21/kxshell-demo.html" title="KXShell的一个Demo">KXShell的一个Demo</a></li><li><a href="http://www.zhangdi.name/2008/09/17/hack-the-parking-game-in-kaixin001.html" title="开心网“争车位”游戏分析（纯技术）">开心网“争车位”游戏分析（纯技术）</a></li><li><a href="http://www.zhangdi.name/2008/09/16/fixing-no-such-file-to-load-mkmf-erro.html" title="解决使用gem安装时出现mkmf找不到的问题">解决使用gem安装时出现mkmf找不到的问题</a></li><li><a href="http://www.zhangdi.name/2008/07/24/add-avatar-to-wordpress-comment-section.html" title="为Wordpress的评论部分加上头像">为Wordpress的评论部分加上头像</a></li><li><a href="http://www.zhangdi.name/2007/10/09/free-ruby-on-rails-book.html" title="Free Ruby on Rails Book">Free Ruby on Rails Book</a></li></ul>]]></content:encoded>
			<wfw:commentRss>http://www.zhangdi.name/2008/08/26/rails-on-vim.html/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Free Ruby on Rails Book</title>
		<link>http://www.zhangdi.name/2007/10/09/free-ruby-on-rails-book.html</link>
		<comments>http://www.zhangdi.name/2007/10/09/free-ruby-on-rails-book.html#comments</comments>
		<pubDate>Tue, 09 Oct 2007 03:36:05 +0000</pubDate>
		<dc:creator>zhangdi</dc:creator>
				<category><![CDATA[Book]]></category>
		<category><![CDATA[RoR]]></category>
		<category><![CDATA[Ruby]]></category>
		<category><![CDATA[书籍]]></category>
		<category><![CDATA[免费]]></category>

		<guid isPermaLink="false">http://www.zhangdi.name/2007/10/09/free-ruby-on-rails-book.html</guid>
		<description><![CDATA[Sitepoint目前提供一本免费的关于Rails的入门书籍（《Build Your Own Ruby on Rails Web Applications》）。它是说60天内免费提供下载，在我写这个Blog的时候还剩下53 days, 4 hours, 26 minutes, 25 seconds。所以如果感兴趣还是尽早去下载吧。:) 大致浏览了一下，这本书可以入门。对Rails可以有一个大致的了解，并且让人知道Rails和Ruby的强大的灵活性和Coding by convention的方便。还是不错的一本书。在书是如此贵的今天，有免费的看，确实是一种恩赐～ 相关文章KXShell的一个Demo开心网“争车位”游戏分析（纯技术）解决使用gem安装时出现mkmf找不到的问题Rails on Vim丑陋的中国人]]></description>
			<content:encoded><![CDATA[<p><!--book ruby rails--></p>
<p>Sitepoint目前提供一本免费的关于Rails的入门书籍（《Build Your Own Ruby on Rails Web Applications》）。它是说60天内免费提供下载，在我写这个Blog的时候还剩下53 days, 4 hours, 26 minutes, 25 seconds。所以如果感兴趣还是尽早去<a href="http://www.sitepoint.com/books/rails1/freebook.php">下载</a>吧。:)</p>
<p>大致浏览了一下，这本书可以入门。对Rails可以有一个大致的了解，并且让人知道Rails和Ruby的强大的灵活性和Coding by convention的方便。还是不错的一本书。在书是如此贵的今天，有免费的看，确实是一种恩赐～</p>
<h3  class="related_post_title">相关文章</h3><ul class="related_post"><li><a href="http://www.zhangdi.name/2008/09/21/kxshell-demo.html" title="KXShell的一个Demo">KXShell的一个Demo</a></li><li><a href="http://www.zhangdi.name/2008/09/17/hack-the-parking-game-in-kaixin001.html" title="开心网“争车位”游戏分析（纯技术）">开心网“争车位”游戏分析（纯技术）</a></li><li><a href="http://www.zhangdi.name/2008/09/16/fixing-no-such-file-to-load-mkmf-erro.html" title="解决使用gem安装时出现mkmf找不到的问题">解决使用gem安装时出现mkmf找不到的问题</a></li><li><a href="http://www.zhangdi.name/2008/08/26/rails-on-vim.html" title="Rails on Vim">Rails on Vim</a></li><li><a href="http://www.zhangdi.name/2007/10/16/the-ugly-chinese.html" title="丑陋的中国人">丑陋的中国人</a></li></ul>]]></content:encoded>
			<wfw:commentRss>http://www.zhangdi.name/2007/10/09/free-ruby-on-rails-book.html/feed</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>当Ruby遇到数独</title>
		<link>http://www.zhangdi.name/2007/09/06/when-ruby-meets-sudoku.html</link>
		<comments>http://www.zhangdi.name/2007/09/06/when-ruby-meets-sudoku.html#comments</comments>
		<pubDate>Thu, 06 Sep 2007 14:33:02 +0000</pubDate>
		<dc:creator>zhangdi</dc:creator>
				<category><![CDATA[Fun]]></category>
		<category><![CDATA[Ruby]]></category>
		<category><![CDATA[数独]]></category>
		<category><![CDATA[游戏]]></category>
		<category><![CDATA[编程]]></category>

		<guid isPermaLink="false">http://www.zhangdi.name/2007/09/06/when-ruby-meets-sudoku.html</guid>
		<description><![CDATA[最近流行一种游戏，叫做“数独”，英文叫Sudoku，听着应该是从日本那边过来的。我曾经做过几个，发现这个东西如果纯粹用眼睛和大脑来解决确实有很大的难度。但是如果你加上纸和笔，那么难度就会降低95%，而如果你借助于更先进的Excell，那么难度就会降低99%。我最终的结论就是，这个东西是个体力劳动。 如果有人还没有接触过数独，那这里就来大概介绍一下：数独应该算是一种九宫格游戏。他是由3*3个九宫格组成的一个大正方形。要求你在9*9个格子里面分别填入适当的1..9的数字，然后让每一行，每一列中的9个数字都包含1..9。另外，每个九宫格中也要包含1..9。下图就是一个数独。 我曾经和LP说过，这个东西实在变态，是一个纯粹的浪费时间的东西。我就异常后悔曾经花了几个人时去做数独。不过，这个月买了《新知客》后，遇到了更变态的事情，那就是，它变态到附赠了一个增刊，其中有28个数独。而且说：“空前震撼！28道数独让你过足瘾！”。更过分的是，其中有些数独本身就是错的（比如，一个九宫格内竟然出现了两个8～）。答案更是错误百出。不知道这些编辑们都是不识数呢，还是不明白数独的规则。 学习Ruby也有一段时间了，突然就想，正好拿这个练习一下。所以花了3个晚上和一个白天的时间用Ruby写了一个解决数独的程序。目前经过我做的一些基本测试，工作还算正常。如果有兴趣，可以在这里下载玩一玩。当然，因为是Ruby，所以还需要Ruby的Interpreter。然后在命令行窗口运行ruby sodoku.rb就可以了。（我是在Windows下写的，所以没有shebang。） 我的感觉就是，用Ruby写程序真的是一种享受。感觉需要用到的东西都是非常straightforward，没有什么要用到的东西需要你自己去费劲配置和研究的。而且大多数API，都可以直接猜出来。比如我写这个的时候，很多用到的API都是先猜着写，然后再看Ruby的API文档，竟然发现没有什么错误。证明了我是一个聪明的人。。。更证明Ruby的API和语法设计的非常友善。呵呵。 我用的算法应该也不是最优的（类似于判别树的算法），但应该比纯粹的枚举要好多了。欢迎讨论，如果大家对算法有兴趣。我正在打算专门写一个网页来介绍我的程序逻辑，不出意外，应该下周一之前写完。欢迎大家提意见。 另外，也有一个计划就是把它变成一个网络应用。不过那就需要更多的测试和调优了。 相关文章用40行程序能展示多少Ruby的特性？Ruby: puts != print + &#8220;\n&#8221;快速解开数独（PySudoku）KXShell的一个Demo开心网“争车位”游戏分析（纯技术）]]></description>
			<content:encoded><![CDATA[<p><!--develop ruby sudoku 数独--></p>
<p>最近流行一种游戏，叫做“数独”，英文叫Sudoku，听着应该是从日本那边过来的。我曾经做过几个，发现这个东西如果纯粹用眼睛和大脑来解决确实有很大的难度。但是如果你加上纸和笔，那么难度就会降低95%，而如果你借助于更先进的Excell，那么难度就会降低99%。我最终的结论就是，这个东西是个体力劳动。</p>
<p>如果有人还没有接触过数独，那这里就来大概介绍一下：数独应该算是一种九宫格游戏。他是由3*3个九宫格组成的一个大正方形。要求你在9*9个格子里面分别填入适当的1..9的数字，然后让每一行，每一列中的9个数字都包含1..9。另外，每个九宫格中也要包含1..9。下图就是一个数独。</p>
<p><a rel="lightbox[]" href="http://www.zhangdi.name/wp-content/gallery/misc/sudoku.PNG" title="sudoku.PNG"><img src="http://www.zhangdi.name/wp-content/gallery/misc/thumbs/thumbs_sudoku.PNG" alt="sudoku.PNG" title="sudoku.PNG" /></a></p>
<p>我曾经和LP说过，这个东西实在变态，是一个纯粹的浪费时间的东西。我就异常后悔曾经花了几个人时去做数独。不过，这个月买了《新知客》后，遇到了更变态的事情，那就是，它变态到附赠了一个增刊，其中有28个数独。而且说：“<strong>空前震撼！28道数独让你过足瘾！</strong>”。更过分的是，其中有些数独本身就是错的（比如，一个九宫格内竟然出现了两个8～）。答案更是错误百出。不知道这些编辑们都是不识数呢，还是不明白数独的规则。</p>
<p>学习Ruby也有一段时间了，突然就想，正好拿这个练习一下。所以花了3个晚上和一个白天的时间用Ruby写了一个解决数独的程序。目前经过我做的一些基本测试，工作还算正常。如果有兴趣，可以在<a href="http://www.zhangdi.name/UserFiles/File/sudoku.zip">这里</a>下载玩一玩。当然，因为是Ruby，所以还需要<a href="http://ruby-lang.org">Ruby的Interpreter</a>。然后在命令行窗口运行ruby sodoku.rb就可以了。（我是在Windows下写的，所以没有shebang。）</p>
<p>我的感觉就是，用Ruby写程序真的是一种享受。感觉需要用到的东西都是非常straightforward，没有什么要用到的东西需要你自己去费劲配置和研究的。而且大多数API，都可以直接猜出来。比如我写这个的时候，很多用到的API都是先猜着写，然后再看Ruby的API文档，竟然发现没有什么错误。证明了我是一个聪明的人。。。更证明Ruby的API和语法设计的非常友善。呵呵。</p>
<p>我用的算法应该也不是最优的（类似于判别树的算法），但应该比纯粹的枚举要好多了。欢迎讨论，如果大家对算法有兴趣。我正在打算专门写一个网页来介绍我的程序逻辑，不出意外，应该下周一之前写完。欢迎大家提意见。</p>
<p>另外，也有一个计划就是把它变成一个网络应用。不过那就需要更多的测试和调优了。</p>
<h3  class="related_post_title">相关文章</h3><ul class="related_post"><li><a href="http://www.zhangdi.name/2007/08/22/a-piece-of-ruby-code.html" title="用40行程序能展示多少Ruby的特性？">用40行程序能展示多少Ruby的特性？</a></li><li><a href="http://www.zhangdi.name/2007/08/21/ruby-puts-not-equals-print-plus-back-slash-n.html" title="Ruby: puts != print + &#8220;\n&#8221;">Ruby: puts != print + &#8220;\n&#8221;</a></li><li><a href="http://www.zhangdi.name/2008/11/17/pysudoku.html" title="快速解开数独（PySudoku）">快速解开数独（PySudoku）</a></li><li><a href="http://www.zhangdi.name/2008/09/21/kxshell-demo.html" title="KXShell的一个Demo">KXShell的一个Demo</a></li><li><a href="http://www.zhangdi.name/2008/09/17/hack-the-parking-game-in-kaixin001.html" title="开心网“争车位”游戏分析（纯技术）">开心网“争车位”游戏分析（纯技术）</a></li></ul>]]></content:encoded>
			<wfw:commentRss>http://www.zhangdi.name/2007/09/06/when-ruby-meets-sudoku.html/feed</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>用40行程序能展示多少Ruby的特性？</title>
		<link>http://www.zhangdi.name/2007/08/22/a-piece-of-ruby-code.html</link>
		<comments>http://www.zhangdi.name/2007/08/22/a-piece-of-ruby-code.html#comments</comments>
		<pubDate>Wed, 22 Aug 2007 07:27:40 +0000</pubDate>
		<dc:creator>zhangdi</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[学习]]></category>
		<category><![CDATA[编程]]></category>

		<guid isPermaLink="false">http://www.zhangdi.name/2007/08/22/a-piece-of-ruby-code.html</guid>
		<description><![CDATA[module OutputHelper def print_line(msg) print msg + "\\n" end end class SayHello include OutputHelper private :print_line def initialize(name, &#38;sayHello) @name, @sayHello = name, sayHello if @sayHello == nil @sayHello = proc { &#124;msg&#124; print_line msg } end end def salute(greet_msg) @sayHello.call("Hello, #{@name}. #{greet_msg}.") end def salute_with_block(greet_msg) if block_given? yield "Hello, #{@name}. I'm using a block. [...]]]></description>
			<content:encoded><![CDATA[<p><!--ruby develop 编程 开发--></p>
<pre name="code" class="ruby">
module OutputHelper
  def print_line(msg)
    print msg + "\\n"
  end
end

class SayHello
  include OutputHelper
  private :print_line
  def initialize(name, &amp;sayHello)
    @name, @sayHello = name, sayHello

    if @sayHello == nil
      @sayHello = proc { |msg| print_line msg }
    end
  end

  def salute(greet_msg)
    @sayHello.call("Hello, #{@name}. #{greet_msg}.")
  end

  def salute_with_block(greet_msg)
    if block_given?
      yield "Hello, #{@name}. I'm using a block. #{greet_msg}."
    else
      @sayHello.call("Hello, #{@name}. You missed the block. #{greet_msg}.")
    end
  end
end

if __FILE__ == $0
  say_hello = SayHello.new("Daniel") { |msg| print msg + "\\n" }
  say_hello.salute("Greetings")
  say_hello.salute_with_block("Greetings")
  say_hello.salute_with_block("Greetings") { |msg| print msg + "\\n" }

  say_hello = SayHello.new("Kimi")
  say_hello.salute("Greetings, again")
end</pre>
<ul>
<li>定义module以及class。</li>
<li>Mixin，将一个module动态include到class里面，使之具有相应的功能。</li>
<li>method的访问级别，private, public等。很多动态语言没有这个功能。</li>
<li>向构造函数传入block类型的参数。</li>
<li>用proc方法构造block。</li>
<li>用block.call方法，调用一个block类型的变量。</li>
<li>用block_given?方法判断是否为一个方法传入了block参数。</li>
<li>用yield来调用为方法传入的block参数。</li>
<li>将测试代码写在if __FILE__ = $0 &#8230; end块中。很类似于Python。</li>
<li>用{|params| expressions }形式定义block。</li>
</ul>
<h3  class="related_post_title">相关文章</h3><ul class="related_post"><li><a href="http://www.zhangdi.name/2007/08/21/ruby-puts-not-equals-print-plus-back-slash-n.html" title="Ruby: puts != print + &#8220;\n&#8221;">Ruby: puts != print + &#8220;\n&#8221;</a></li><li><a href="http://www.zhangdi.name/2007/09/06/when-ruby-meets-sudoku.html" title="当Ruby遇到数独">当Ruby遇到数独</a></li><li><a href="http://www.zhangdi.name/2007/05/21/research-on-stringtable-in-vcpp.html" title="VC++2005 StringTable资源类型研究">VC++2005 StringTable资源类型研究</a></li><li><a href="http://www.zhangdi.name/2007/03/18/learn-design-pattern-without-coding-and-class-diagram-2.html" title="不用代码和类图说设计模式（2）">不用代码和类图说设计模式（2）</a></li><li><a href="http://www.zhangdi.name/2007/03/17/learn-design-pattern-without-coding-and-class-diagram-1.html" title="不用代码和类图说设计模式（1）">不用代码和类图说设计模式（1）</a></li></ul>]]></content:encoded>
			<wfw:commentRss>http://www.zhangdi.name/2007/08/22/a-piece-of-ruby-code.html/feed</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
		<item>
		<title>Ruby: puts != print + &#8220;\n&#8221;</title>
		<link>http://www.zhangdi.name/2007/08/21/ruby-puts-not-equals-print-plus-back-slash-n.html</link>
		<comments>http://www.zhangdi.name/2007/08/21/ruby-puts-not-equals-print-plus-back-slash-n.html#comments</comments>
		<pubDate>Tue, 21 Aug 2007 14:18:36 +0000</pubDate>
		<dc:creator>zhangdi</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[学习]]></category>
		<category><![CDATA[源码分析]]></category>
		<category><![CDATA[编程]]></category>

		<guid isPermaLink="false">http://www.zhangdi.name/2007/08/21/ruby-puts-print-n.html</guid>
		<description><![CDATA[今天看到railschina论坛上一篇贴子在讨论在Ruby中，puts str是不是等于print str + &#8220;\n&#8221;。因为一位同学做了实验，在irb中，在多线程环境下使用puts似乎有问题，有的时候字符串和换行的顺序会乱，而用print就没有问题，所以得出结论，认为puts是不等于print + &#8220;\n&#8221;的。又有人提出质疑，因为做了另外的实验，在非irb环境下，puts和print都没有问题，所以认为多线程问题只是主观臆测，有可能是irb的问题。甚至还有人写信给Dave，结果Dave也没有给出明确的答复～ 正好手头上有Ruby的源代码，所以翻出来看了一下，在io.c中，明确的写明了Ruby中ios.puts方法的实现： VALUE rb_io_puts(argc, argv, out) int argc; VALUE *argv; VALUE out; { int i; VALUE line; /* if no argument given, print newline. */ if (argc == 0) { rb_io_write(out, rb_default_rs); return Qnil; } for (i=0; i&#60;argc; i++) { if (NIL_P(argv[i])) { line = rb_str_new2("nil"); } else { [...]]]></description>
			<content:encoded><![CDATA[<p><!--ruby develop 编程 开发--></p>
<p>今天看到railschina论坛上一篇贴子在讨论在Ruby中，puts str是不是等于print str + &#8220;\n&#8221;。因为一位同学做了实验，在irb中，在多线程环境下使用puts似乎有问题，有的时候字符串和换行的顺序会乱，而用print就没有问题，所以得出结论，认为puts是不等于print + &#8220;\n&#8221;的。又有人提出质疑，因为做了另外的实验，在非irb环境下，puts和print都没有问题，所以认为多线程问题只是主观臆测，有可能是irb的问题。甚至还有人写信给Dave，结果Dave也没有给出明确的答复～</p>
<p>正好手头上有Ruby的源代码，所以翻出来看了一下，在io.c中，明确的写明了Ruby中ios.puts方法的实现：</p>
<pre name="code" class="cpp:collapse">
VALUE
rb_io_puts(argc, argv, out)
    int argc;
    VALUE *argv;
    VALUE out;
{
   int i;
   VALUE line; 

   /* if no argument given, print newline. */
   if (argc == 0) {
      rb_io_write(out, rb_default_rs);
      return Qnil;
   }
   for (i=0; i&lt;argc; i++) {
      if (NIL_P(argv[i])) {
         line = rb_str_new2("nil");
      }
      else {
         line = rb_check_array_type(argv[i]);
         if (!NIL_P(line)) {
            rb_protect_inspect(io_puts_ary, line, out);
            continue;
         }
         line = rb_obj_as_string(argv[i]);
      }
      rb_io_write(out, line);
      if (RSTRING(line)-&gt;len == 0 ||
            RSTRING(line)-&gt;ptr[RSTRING(line)-&gt;len-1] != '\n') {
         rb_io_write(out, rb_default_rs);
      }
   } 

   return Qnil;
}</pre>
<p>可以看到27行和30行就是分别向流中写我们传入的string和&#8221;\n&#8221;的代码，所以puts确实是<strong>存在潜在的多线程问题</strong>的。而对于print str + &#8220;\n&#8221;这种方式，因为ruby会先把str和&#8221;\n&#8221;构造为一个新的string，然后再传给print函数，所以是没有这种问题的。总结：在Ruby中，<strong>puts != print + &#8220;\n&#8221;</strong></p>
<p>另外，如果用print(str1, str2)这种形式，同样会有多线程问题。因为在Ruby中，print的实现是，一个一个参数分别写入流，而不是先将参数合并，再一次写入。（合并参数会占用额外的内存，多次IO又会消耗时间，不知道最初Ruby是如何权衡这个的～）</p>
<h3  class="related_post_title">相关文章</h3><ul class="related_post"><li><a href="http://www.zhangdi.name/2007/08/22/a-piece-of-ruby-code.html" title="用40行程序能展示多少Ruby的特性？">用40行程序能展示多少Ruby的特性？</a></li><li><a href="http://www.zhangdi.name/2007/09/06/when-ruby-meets-sudoku.html" title="当Ruby遇到数独">当Ruby遇到数独</a></li><li><a href="http://www.zhangdi.name/2007/05/21/research-on-stringtable-in-vcpp.html" title="VC++2005 StringTable资源类型研究">VC++2005 StringTable资源类型研究</a></li><li><a href="http://www.zhangdi.name/2007/03/18/learn-design-pattern-without-coding-and-class-diagram-2.html" title="不用代码和类图说设计模式（2）">不用代码和类图说设计模式（2）</a></li><li><a href="http://www.zhangdi.name/2007/03/17/learn-design-pattern-without-coding-and-class-diagram-1.html" title="不用代码和类图说设计模式（1）">不用代码和类图说设计模式（1）</a></li></ul>]]></content:encoded>
			<wfw:commentRss>http://www.zhangdi.name/2007/08/21/ruby-puts-not-equals-print-plus-back-slash-n.html/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

