<?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; regex</title>
	<atom:link href="http://iregex.org/blog/tag/regex/feed" rel="self" type="application/rss+xml" />
	<link>http://iregex.org</link>
	<description>原创、翻译、转载关于正则表达式的文章</description>
	<lastBuildDate>Sun, 27 Jun 2010 04:20:24 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.0</generator>
<atom:link rel="hub" href="http://pubsubhubbub.appspot.com"/><atom:link rel="hub" href="http://superfeedr.com/hubbub"/><atom:link rel="hub" href="http://www.feedsky.com/api/RPC2"/><atom:link rel="hub" href="http://blogsearch.google.com/ping/RPC2"/><atom:link rel="hub" href="http://blog.yodao.com/ping/RPC2"/><atom:link rel="hub" href="http://www.feedsky.com/api/RPC2"/><atom:link rel="hub" href="http://www.xianguo.com/xmlrpc/ping.php"/><atom:link rel="hub" href="http://www.zhuaxia.com/rpc/server.php"/><atom:link rel="hub" href="http://rpc.technorati.com/rpc/ping"/><atom:link rel="hub" href="http://rpc.pingomatic.com/"/>	
<!-- Start Of Script Generated By WP-PostViews Plus -->
<script type='text/javascript' src='http://iregex.org/wp-includes/js/jquery/jquery.js?ver=1.4.2'></script>
<script type="text/javascript">
/* <![CDATA[ */
/* ]]> */
</script>
<!-- End Of Script Generated By WP-PostViews Plus -->
	<item>
		<title>笔记：如何写出高效率的正则表达式</title>
		<link>http://iregex.org/blog/regex-optimizing.html</link>
		<comments>http://iregex.org/blog/regex-optimizing.html#comments</comments>
		<pubDate>Mon, 30 Nov 2009 14:53:26 +0000</pubDate>
		<dc:creator>rex</dc:creator>
				<category><![CDATA[教程]]></category>
		<category><![CDATA[efficiency]]></category>
		<category><![CDATA[optimize]]></category>
		<category><![CDATA[regex]]></category>

		<guid isPermaLink="false">http://iregex.org/?p=71</guid>
		<description><![CDATA[如果纯粹是为了挑战自己的正则水平，用来实现一些特效（例如使用正则表达式计算质数、解线性方程），效率不是问题；如果所写的正则表达式只是为了满足一两次、几十次的运行，优化与... ]]></description>
			<content:encoded><![CDATA[<p>如果纯粹是为了挑战自己的正则水平，用来实现一些特效（例如使用正则表达式计算质数、解线性方程），效率不是问题；如果所写的正则表达式只是为了满足一两次、几十次的运行，优化与否区别也不太大。但是，如果所写的正则表达式会百万次、千万次地运行，效率就是很大的问题了。我这里总结了几条提升正则表达式运行效率的经验（工作中学到的，看书学来的，自己的体会），贴在这里。如果您有其它的经验而这里没有提及，欢迎赐教。</p>
<p>为行文方便，先定义两个概念。</p>
<ul>
<li><b>误匹配</b>：指正则表达式所匹配的内容范围超出了所需要范围，有些文本明明不符合要求，但是被所写的正则式“击中了”。例如，如果使用<font color="#3366ff">\d{11}</font>来匹配11位的手机号，<font color="#3366ff">\d{11}</font>不单能匹配正确的手机号，它还会匹配<font color="#cc33cc">98765432100</font>这样的明显不是手机号的字符串。我们把这样的匹配称之为误匹配。</li>
<li><b>漏匹配</b>：指正则表达式所匹配的内容所规定的范围太狭窄，有些文本确实是所需要的，但是所写的正则没有将这种情况囊括在内。例如，使用<font color="#3366ff">\d{18}</font>来匹配18位的身份证号码，就会漏掉结尾是字母X的情况。
</li>
</ul>
<p>写出一条正则表达式，既可能<b>只出现</b>误匹配（条件写得极宽松，其范围大于目标文本），也可能<b>只出现</b>漏匹配（只描述了目标文本中多种情况种的一种），还可能<b>既有误匹配又有漏匹配</b>。例如，使用<font color="#3366ff">\w+\.com</font>来匹配.com结尾的域名，既会误匹配<font color="#cc33cc">abc_.com</font>这样的字串（合法的域名中不含下划线，<font color="#3366ff">\w</font>包含了下划线这种情况），又会漏掉<font color="#cc33cc">ab-c.com</font>这样的域名（合法域名中可以含中划线，但是<font color="#3366ff">\w</font>不匹配中划线）。</p>
<p>精准的正则表达式意味着既无误匹配且无漏匹配。当然，现实中存在这样的情况：只能看到有限数量的文本，根据这些文本写规则，但是这些规则将会用到海量的文本中。这种情况下，尽可能地（如果不是完全地）消除误匹配以及漏匹配，并提升运行效率，就是我们的目标。本文所提出的经验，主要是针对这种情况。</p>
<ol>
<li><b>掌握语法细节</b>。正则表达式在各种语言中，其语法大致相同，细节各有千秋。明确所使用语言的正则的语法的细节，是写出正确、高效正则表达式的基础。例如，perl中与<font color="#3366ff">\w</font>等效的匹配范围是<font color="#3366ff">[a-zA-Z0-9_]</font>；perl正则式不支持肯定逆序环视中使用可变的重复（variable repetition inside lookbehind，例如<font color="#3366ff">(?&lt;=.*)abc</font>），但是.Net语法是支持这一特性的；又如，JavaScript连逆序环视（Lookbehind,如<font color="#3366ff">(?&lt;=ab)c</font>）都不支持，而perl和python是支持的。《精通正则表达式》第3章《正则表达式的特性和流派概览》明确地列出了各大派系正则的异同，<a target="_blank" href="http://iregex.org/blog/regex-syntax-comparison.html">这篇文章</a>也简要地列出了几种常用语言、工具中正则的比较。对于具体使用者而言，至少应该详细了解正在使用的那种工作语言里正则的语法细节。</li>
<li><b>先粗后精，</b><b>先加后减</b>。使用正则表达式语法对于目标文本进行描述和界定，可以像画素描一样，先大致勾勒出框架，再逐步在局步实现细节。仍举刚才的手机号的例子，先界定<font color="#3366ff">\d{11}</font>，总不会错；再细化为<font color="#3366ff">1[358]\d{9}</font>，就向前迈了一大步（至于第二位是不是3、5、8，这里无意深究，只举这样一个例子，说明逐步细化的过程）。这样做的目的是先消除漏匹配（刚开始先尽可能多地匹配，做加法），然后再一点一点地消除误匹配（做减法）。这样有先有后，在考虑时才不易出错，从而向“不误不漏”这个目标迈进。</li>
<li><b>留有余地</b>。所能看到的文本sample是有限的，而待匹配检验的文本是海量的，暂时不可见的。对于这样的情况，在写正则表达式时要跳出所能见到的文本的圈子，开拓思路，作出“战略性前瞻”。例如，经常收到这样的垃圾短信：“发*票”、“发#漂”。如果要写规则屏蔽这样烦人的垃圾短信，不但要能写出可以匹配当前文本的正则表达式 <font color="#3366ff">发[*#](?:票|漂)</font>，还要能够想到 <font color="#3366ff">发.(?:票|漂|飘)</font>之类可能出现的“变种”。这在具体的领域或许会有针对性的规则，不多言。这样做的目的是消除漏匹配，延长正则表达式的生命周期。
</li>
<li><b>明确</b>。具体说来，就是<b>谨慎</b>用点号这样的元字符，<b>尽可能</b>不用星号和加号这样的任意量词。只要能确定范围的，例如\w，就不要用点号；只要能够预测重复次数的，就不要用任意量词。例如，写析取twitter消息的脚本，假设一条消息的xml正文部分结构是&lt;span class=&#8221;msg&#8221;&gt;&#8230;&lt;/span&gt;且正文中无尖括号，那么<font color="#3366ff">&lt;span class=&#8221;msg&#8221;&gt;[^&lt;]{1,480}&lt;/span&gt;</font>这种写法<b>的思路</b>要好于<font color="#3366ff">&lt;span class=&#8221;msg&#8221;&gt;.*&lt;/span&gt;</font>，原因有二：一是使用<font color="#3366ff">[^&lt;]</font>，它保证了文本的范围不会超出下一个小于号所在的位置；二是明确长度范围，<font color="#3366ff">{1,480}</font>，其依据是一条twitter消息大致能的字符长度范围。当然，480这个长度是否正确还可推敲，但是这种思路是值得借鉴的。说得狠一点，“滥用点号、星号和加号是不环保、不负责任的做法”。</li>
<li><b>不要让稻草压死骆驼</b>。每使用一个普通括号()而不是非捕获型括号<font color="#3366ff">(?:&#8230;)</font>，就会保留一部分内存等着你再次访问。这样的正则表达式、无限次地运行次数，无异于一根根稻草的堆加，终于能将骆驼压死。养成合理使用(?:&#8230;)括号的习惯。</li>
<li><b>宁简勿繁</b>。将一条复杂的正则表达式拆分为两条或多条简单的正则表达式，编程难度会降低，运行效率会提升。例如用来消除行首和行尾空白字符的正则表达式<font color="#3366ff">s/^\s+|\s+$//g;</font>，其运行效率理论上要低于<font color="#3366ff">s/^\s+//g; s/\s+$//g;</font> 。这个例子出自《精通正则表达式》第五章，书中对它的评论是“它几乎总是最快的，而且显然最容易理解”。既快又容易理解，何乐而不为？工作中我们还有其它的理由要将C==<font color="#3366ff">(A|B)</font>这样的正则表达式拆为A和B两条表达式分别执行。例如，虽然A和B这两种情况只要有一种能够击中所需要的文本模式就会成功匹配，但是如果只要有一条子表达式（例如A）会产生误匹配，那么不论其它的子表达式（例如B）效率如何之高，范围如何精准，C的总体精准度也会因A而受到影响。</li>
<li><b>巧妙定位</b>。有时候，我们需要匹配的the，是作为单词的the（两边有空格），而不是作为单词一部分的t-h-e的有序排列（例如toge<font color="#cc33cc">the</font>r中的the）。在适当的时候用上<font color="#3366ff">^</font>，<font color="#3366ff">$</font>，<font color="#3366ff">\b</font>等等定位锚点，能有效提升找到成功匹配、淘汰不成功匹配的效率。
</li>
</ol>
<p>总结完发现，《精通正则表达式》的第5章、第6章已经以更为有条理的方式总结出了常用的优化方法。不过，泛泛地读过的印象是肤浅的，过后即忘的；而真正若有所悟时在书上得到了系统地印证，这种感觉才是真的爽。</p>
]]></content:encoded>
			<wfw:commentRss>http://iregex.org/blog/regex-optimizing.html/feed</wfw:commentRss>
		<slash:comments>9</slash:comments>
		</item>
		<item>
		<title>正则杂谈：从&#8220;评论已关闭&#8221;到正则表达式之眼</title>
		<link>http://iregex.org/blog/from-comment-closed-to-regex-crafting.html</link>
		<comments>http://iregex.org/blog/from-comment-closed-to-regex-crafting.html#comments</comments>
		<pubDate>Wed, 27 May 2009 02:07:50 +0000</pubDate>
		<dc:creator>rex</dc:creator>
				<category><![CDATA[杂项]]></category>
		<category><![CDATA[regex]]></category>

		<guid isPermaLink="false">http://iregex.org/blog/from-comment-closed-to-regex-crafting.html</guid>
		<description><![CDATA[近来沸沸扬扬地一条饭否消息是评论已关闭，这个关键词真的选的很好，它一下子把所有的一类敏感问题都串起来了，找到了该类问题的共同特征。至于为什么关闭评论，关闭的标准是什么，... ]]></description>
			<content:encoded><![CDATA[<p>近来沸沸扬扬地一条饭否消息是<a href="http://fanfou.com/home#search?q=%E8%AF%84%E8%AE%BA%E5%B7%B2%E5%85%B3%E9%97%AD" rel="nofollow" target="_blank">评论已关闭</a>，这个关键词真的选的很好，它一下子把所有的一类敏感问题都串起来了，找到了该类问题的共同特征。至于为什么关闭评论，关闭的标准是什么，这里都不做探讨，只是从正则角度谈论一下技术而已。</p>
<p>所谓正则表达式，其实是一种抽象，是从现有的文本中找到规律，然后用正则的语言描述出来。例如，上次有人问，以http开头的，以空格结尾的正则式如何写？这个问题不难，我们只要符合这两个要求即可，即^(http\S+)\s。至于http后面的冒号、双斜杠，都不必劳神去匹配。这样写出来的正则表达式简洁明快，清晰易读。当然，从效率出发，越精确的正则式越有利于尽早失败，有利于提升效率。权衡写的效率与执行的效率，其过程也是很不错的。</p>
]]></content:encoded>
			<wfw:commentRss>http://iregex.org/blog/from-comment-closed-to-regex-crafting.html/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Windows下的正则表达式工具之五——经典的Regulator</title>
		<link>http://iregex.org/blog/regulator.html</link>
		<comments>http://iregex.org/blog/regulator.html#comments</comments>
		<pubDate>Wed, 17 Dec 2008 15:55:44 +0000</pubDate>
		<dc:creator>rex</dc:creator>
				<category><![CDATA[软件]]></category>
		<category><![CDATA[expresso]]></category>
		<category><![CDATA[regex]]></category>
		<category><![CDATA[regexbuddy]]></category>
		<category><![CDATA[regulator]]></category>
		<category><![CDATA[tool]]></category>

		<guid isPermaLink="false">http://iregex.org/?p=40</guid>
		<description><![CDATA[本文介绍的the Regulator 2.0 与上一篇文章介绍的Expresso一样，都是颇有年头的软件：Expresso的最后更新日期似乎是2007年6月30日；the Regulator 2.0的上次更新，更是可追溯到2004年。可是，在没有RegexBudd... ]]></description>
			<content:encoded><![CDATA[<p><img style="border-bottom: rgb(255,255,255) 1px solid; border-left: rgb(255,255,255) 1px solid; margin: 0px 10px 10px; padding-left: 0px; float: right; clear: both; border-top: rgb(255,255,255) 1px solid; border-right: rgb(255,255,255) 1px solid" src="http://i293.photobucket.com/albums/mm60/zhasm/regulator_logo.png"> 本文介绍的the Regulator 2.0 与上一篇文章介绍的<a href="http://iregex.org/blog/expresso.html" title="Expresso|http://iregex.org|我爱正则表达式" target="_blank">Expresso</a>一样，都是颇有年头的软件：Expresso的最后更新日期似乎是2007年6月30日；the Regulator 2.0的上次更新，更是可追溯到2004年。可是，在没有RegexBuddy的日子里，the Regulator 可算是元老呢！MSDN上有篇文章《<a target="_blank" href="http://msdn.microsoft.com/zh-cn/magazine/cc300497(en-us).aspx">Ten Must-Have Tools Every Developer Should Download Now</a>》，介绍了开发者必备的10款工具之一就有the <a href="http://iregex.org/blog/regulator.html" title="Regulator|http://iregex.org|我爱正则表达式" target="_blank">Regulator</a>。作者<a target="_blank" href="http://weblogs.asp.net/rosherove/">Roy Osherove</a>在regulator的帮助文件中说，自己的Regulator的创意就来自于<a href="http://iregex.org/blog/expresso.html" title="Expresso|http://iregex.org|我爱正则表达式" target="_blank">Expresso</a>。</p>
<p><a href="http://iregex.org/blog/regulator.html" title="Regulator|http://iregex.org|我爱正则表达式" target="_blank">Regulator</a>的界面，比<a href="http://iregex.org/blog/expresso.html" title="Expresso|http://iregex.org|我爱正则表达式" target="_blank">Expresso</a>要新潮，与以前介绍过的Mtracer有几分相像。<span id="more-40"></span>看界面：<img src="http://i293.photobucket.com/albums/mm60/zhasm/regulator_main.png" width=540> </p>
<p>与<a href="http://iregex.org/blog/expresso.html" title="Expresso|http://iregex.org|我爱正则表达式" target="_blank">Expresso</a>一样，它同样支持.Net版的正则，支持将正则式导出为VB或C#格式。比起<a href="http://iregex.org/blog/expresso.html" title="Expresso|http://iregex.org|我爱正则表达式" target="_blank">Expresso</a>来，它的亮点之一是正则式部分支持语法高亮显示。</p>
<p><a href="http://iregex.org/blog/regulator.html" title="Regulator|http://iregex.org|我爱正则表达式" target="_blank">Regulator</a>有一个功能是网络搜索，即支持在软件界面上直接搜索regexlib.com上的正则代码库。这原本应该是个很实用的功能。可惜的是，我在多种情况下（代理）试用了该功能，一直不能返回搜索结果。或许是随着时间的迁移，regexlib.com更换了查询输出接口，而<a href="http://iregex.org/blog/regulator.html" title="Regulator|http://iregex.org|我爱正则表达式" target="_blank">Regulator</a>还站在望夫涯上，傻傻地使用原来的方式与regexlib.com通讯，自然接收不到任何反馈。</p>
<p>帮助文件中的搜索结果列表：<br /><img src="http://i293.photobucket.com/albums/mm60/zhasm/regulator_search_old.png"> </p>
<p>这是在我的机器上返回的空列表：<br /><img src="http://i293.photobucket.com/albums/mm60/zhasm/regulator_search.png"> </p>
<p>我登录到作者<a target="_blank" href="http://weblogs.asp.net/rosherove/">Roy Osherove</a>的博客，搜索到他的一些其它正则式项目，例如2006年10月份的<a target="_blank" href="http://weblogs.asp.net/rosherove/archive/2006/10/09/Regulazy-1.0.3-Released.aspx">Realazy</a>（将普通文本转换为正则表达式的小工具，比较傻瓜），2005年11月份的VS2005下的正则式可视化工具（<a target="_blank" href="http://weblogs.asp.net/rosherove/archive/2005/11/26/AnnoucingRegexKit10.aspx">Regular Expression Visualizers for VS 2005</a>），只可惜最近两年没有在正则式方面更新文章或软件。因此该软件估计以后也不会更新了吧。作为一款经典的免费的正则式软件，估计<a href="http://iregex.org/blog/regulator.html" title="Regulator|http://iregex.org|我爱正则表达式" target="_blank">Regulator</a>曾经风光一时；不过，在我接触正则式时起，一直用的就是Regex了。</p>
<p>最近搜集了一大堆网页正则式工具，有时间跟大家分享一下。敬请期待。 </p>
<p>附：the Regulator 2.0 (3.2MB)下载地址：via <a href="http://downloads.sourceforge.net/regulator/Regulator20Bin.zip?modtime=1189740236&#038;big_mirror=0" title="the Regulator|http://iregex.org/|我爱正则表达式">sourceforge</a> | via <a href="http://zhasm.com/downloads#regulator" target="_blank">深柳堂</a></p>
]]></content:encoded>
			<wfw:commentRss>http://iregex.org/blog/regulator.html/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>饭否消息解析之从minidom到xpath</title>
		<link>http://iregex.org/blog/fanfou-message-extractor-from-minidom-to-xpath.html</link>
		<comments>http://iregex.org/blog/fanfou-message-extractor-from-minidom-to-xpath.html#comments</comments>
		<pubDate>Tue, 14 Oct 2008 10:00:58 +0000</pubDate>
		<dc:creator>rex</dc:creator>
				<category><![CDATA[教程]]></category>
		<category><![CDATA[fanfou]]></category>
		<category><![CDATA[firefox]]></category>
		<category><![CDATA[python]]></category>
		<category><![CDATA[regex]]></category>
		<category><![CDATA[xml]]></category>
		<category><![CDATA[xpath]]></category>

		<guid isPermaLink="false">http://iregex.org/?p=35</guid>
		<description><![CDATA[抛板砖，引白玉：为何不用xpath，什么是xpath？ 最近拾起了以前的小项目，在完善上篇文章发布后，“那个谁”的回复让我很感兴趣。他问，“为什么不用xpath？” xpath是什么东东？我反问。反... ]]></description>
			<content:encoded><![CDATA[<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;">抛板砖，引白玉：为何不用xpath，什么是xpath？</h2>
<p>最近拾起了以前的小项目，在完善<a href="http://iregex.org/blog/fanfou-message-extractor-regex-vs-xml.html">上篇文章</a>发布后，“那个谁”的回复让我很感兴趣。他问，“为什么不用xpath？”</p>
<p>xpath是什么东东？我反问。反问之前，当然少不了先google一番，以免……那个啥。<br />
<span id="more-35"></span><br />
首先映入眼帘的是<a href="http://www.w3c.org/TR/xpath">w3c</a> ，对xpath的介绍如下：</p>
<blockquote style="border-left:2px solid #DDDDDD; margin:15px 30px 0 10px; padding-left:20px;"><p>XPath is a language for addressing parts of an XML document, designed to be used by both XSLT and XPointer. </p></blockquote>
<p>直译为中文就是，</p>
<blockquote style="border-left:2px solid #DDDDDD; margin:15px 30px 0 10px; padding-left:20px;"><p>XPath 是一种语言，用于在XML文档中定位各部分内容，可由XSLT或XPointer调用。</p></blockquote>
<p>还搜索到<a href="http://www.zvon.org/xxl/XPathTutorial/General/examples.html">xpath</a>的教程，在这里。草草看过，当时并未着意。</p>
<p>虽如此，但是python里的minidom模块，也有此功效呀。为什么非要使用xpath呢？尤其是考虑到在python中还需要额外安装，不如minidom之放之四海而皆可运行。</p>
<p>跟那个谁再交流，意见仍是“力荐”。还推荐我细读<a href="http://www.zvon.org/xxl/XPathTutorial/General/examples.html">教程</a>，并在firefox里使用<a href="https://addons.mozilla.org/zh-CN/firefox/addon/1095">XPath Checker</a>插件。</p>
<p>于是就照办了。</p>
<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;">发硎新试,其快可知</h2>
<p>一试XPath Checker，果然石破天惊。选中部分网页文字后，在右键菜单中选&#8221;View Xpath&#8221;，立即显示出该节点的XPath路径。层次清晰，定位精准。只是我对其语法尚未了了。于是细读教程，边学边用；半小时后，已经能够运用到之前写的饭否信息抓取程序上。虽然写代码还有些吃力，但是思路很清晰，不会纠缠于细节中无法脱身。</p>
<p>那个谁还提议，一般的html文档不是标准的xml文档，因此用xpath解析时，最好格式化一下。</p>
<p>我也注意到这个问题了。从饭否html中取出的有用内容，只占全文的一小部分；额外的部分白白拖慢速度，增强析取难度。</p>
<p>经过实验，我将原代码改进如下：</p>
<p>1. 仍用原来的minidom模块下载、分析文档，只取&lt;ol&gt;与&lt;/ol&gt;之间的部分。这部分保存成字符串格式，备用。只取需要的那部分，使结构清晰，层次浅显。</p>
<p>2. 使用xpath来解析上一步取出的字串。</p>
<p>到现在，/，//，@，[]，=，等等，每个符号都从原来的meaningless变成helpful，在我的工具箱中有了合适的位置，随取随用，十分方便。我已经成了xpath的受益者。现在才觉得学习xpath真是很有趣、有用。</p>
<p>目前还有个小问题，无法使用纯粹的xpath语法解决。问题描述如下：</p>
<p>xpath只能解析实体内容，不能&#8221;囫囵吞枣&#8221;地解析。例如：</p>
<div class="codecolorer-container xml mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br /></div></td><td><div class="xml codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;li<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;a</span> <span style="color: #000066;">href</span>=<span style="color: #ff0000;">'http://a.com'</span><span style="color: #000000; font-weight: bold;">&gt;</span></span>hello world<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/a<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/li<span style="color: #000000; font-weight: bold;">&gt;</span></span></span></div></td></tr></tbody></table></div>
<p>在view xpath 下，使用/li/a，得到的是</p>
<div class="codecolorer-container xml mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="xml codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;a</span> <span style="color: #000066;">href</span>=<span style="color: #ff0000;">'http://a.com'</span><span style="color: #000000; font-weight: bold;">&gt;</span></span>hello world<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/a<span style="color: #000000; font-weight: bold;">&gt;</span></span></span></div></td></tr></tbody></table></div>
<p>全部内容；</p>
<p>但是在python下，使用</p>
<div class="codecolorer-container python mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="python codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">method=doc.<span style="color: black;">xpath</span><span style="color: black;">&#40;</span>u<span style="color: #483d8b;">''</span><span style="color: #483d8b;">'string(/li/a)'</span><span style="color: #483d8b;">''</span><span style="color: black;">&#41;</span></div></td></tr></tbody></table></div>
<p>虽然，也能通过/li/a/@href得到&#8217;http://a.com&#8217;的内容。</p>
<p>却只能得到hello world。xpath把所有的&lt;&gt;之内的东西给消灭掉了。很诡异。</p>
<p>遇到这种情况，如果我想得到整条的信息，就使用list.childNodes[index-1].firstChild.toxml()[22:-7]这种变通方式。不过，之前的doc = Parse(str(list.toxml()))我觉得用得挺好，是自己的一个&#8221;创举&#8221;，在程序中再度使用一下传统的xml解析方式，也无可厚非。当然，如果能够在xpath下把上述所有的事情都处理掉，是最好的。</p>
<p>经过了一点点的修补、改进，最终的饭否消息程序如下（核心代码部分）：</p>
<div class="codecolorer-container python mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;height:300px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br />17<br />18<br />19<br />20<br />21<br />22<br />23<br />24<br />25<br />26<br />27<br /></div></td><td><div class="python codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&nbsp; &nbsp; <span style="color: #ff7700;font-weight:bold;">def</span> __getMsgByPage__<span style="color: black;">&#40;</span><span style="color: #008000;">self</span>,page<span style="color: black;">&#41;</span>:<br />
<br />
&nbsp; &nbsp; &nbsp; &nbsp; url=<span style="color: #483d8b;">&quot;http://fanfou.com/&quot;</span>+<span style="color: #008000;">self</span>.<span style="color: #dc143c;">user</span>+<span style="color: #483d8b;">&quot;/p.&quot;</span>+<span style="color: #008000;">str</span><span style="color: black;">&#40;</span>page<span style="color: black;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; node = minidom.<span style="color: black;">parse</span><span style="color: black;">&#40;</span><span style="color: #dc143c;">urllib2</span>.<span style="color: black;">urlopen</span><span style="color: black;">&#40;</span>url<span style="color: black;">&#41;</span><span style="color: black;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #008000;">list</span> = node.<span style="color: black;">getElementsByTagName</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;ol&quot;</span><span style="color: black;">&#41;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span><span style="color: black;">&#93;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; doc = Parse<span style="color: black;">&#40;</span><span style="color: #008000;">str</span><span style="color: black;">&#40;</span><span style="color: #008000;">list</span>.<span style="color: black;">toxml</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; cu=<span style="color: #008000;">self</span>.<span style="color: black;">sql</span>.<span style="color: black;">cursor</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #008000;">max</span>=doc.<span style="color: black;">xpath</span><span style="color: black;">&#40;</span>u<span style="color: #483d8b;">''</span><span style="color: #483d8b;">'count(/ol/li)'</span><span style="color: #483d8b;">''</span><span style="color: black;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #008000;">max</span>=<span style="color: #008000;">int</span><span style="color: black;">&#40;</span><span style="color: #008000;">max</span><span style="color: black;">&#41;</span>+<span style="color: #ff4500;">1</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #ff7700;font-weight:bold;">if</span> <span style="color: #008000;">max</span>==<span style="color: #ff4500;">1</span>:<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #ff7700;font-weight:bold;">return</span> <span style="color: #ff4500;">0</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #008000;">max</span>=<span style="color: #008000;">int</span><span style="color: black;">&#40;</span><span style="color: #008000;">max</span><span style="color: black;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #ff7700;font-weight:bold;">for</span> index <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">range</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>,<span style="color: #008000;">max</span><span style="color: black;">&#41;</span>:<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; method=doc.<span style="color: black;">xpath</span><span style="color: black;">&#40;</span>u<span style="color: #483d8b;">''</span><span style="color: #483d8b;">'string(/ol/li[%d]//span[@class='</span>method<span style="color: #483d8b;">'])'</span><span style="color: #483d8b;">''</span> <span style="color: #66cc66;">%</span> index<span style="color: black;">&#41;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">2</span>:<span style="color: black;">&#93;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; method=method.<span style="color: black;">replace</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">' '</span>,<span style="color: #483d8b;">''</span><span style="color: black;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #ff7700;font-weight:bold;">if</span> method==<span style="color: #483d8b;">&quot;彩信&quot;</span>:<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #dc143c;">time</span>=doc.<span style="color: black;">xpath</span><span style="color: black;">&#40;</span>u<span style="color: #483d8b;">''</span><span style="color: #483d8b;">'string(/ol/li[%d]//span[@class=&quot;time&quot;]/@title)'</span><span style="color: #483d8b;">''</span>\<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #66cc66;">%</span> index<span style="color: black;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; uuid=doc.<span style="color: black;">xpath</span><span style="color: black;">&#40;</span>u<span style="color: #483d8b;">''</span><span style="color: #483d8b;">'string(/ol/li[%d]//a[@class='</span>photo<span style="color: #483d8b;">']/@href)'</span><span style="color: #483d8b;">''</span>\<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #66cc66;">%</span> index<span style="color: black;">&#41;</span> <span style="color: black;">&#91;</span>-<span style="color: #ff4500;">11</span>:<span style="color: black;">&#93;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #ff7700;font-weight:bold;">else</span>:<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #dc143c;">time</span>=doc.<span style="color: black;">xpath</span><span style="color: black;">&#40;</span>u<span style="color: #483d8b;">''</span><span style="color: #483d8b;">'string(/ol/li[%d]//a[@class='</span><span style="color: #dc143c;">time</span><span style="color: #483d8b;">']/@title)'</span><span style="color: #483d8b;">''</span>\<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #66cc66;">%</span> index<span style="color: black;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; uuid=doc.<span style="color: black;">xpath</span><span style="color: black;">&#40;</span>u<span style="color: #483d8b;">''</span><span style="color: #483d8b;">'string(/ol/li[%d]//a[@class='</span><span style="color: #dc143c;">time</span><span style="color: #483d8b;">']/@href)'</span><span style="color: #483d8b;">''</span> <span style="color: #66cc66;">%</span> index<span style="color: black;">&#41;</span><span style="color: black;">&#91;</span>-<span style="color: #ff4500;">11</span>:<span style="color: black;">&#93;</span><br />
<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; content = <span style="color: #008000;">list</span>.<span style="color: black;">childNodes</span><span style="color: black;">&#91;</span>index-<span style="color: #ff4500;">1</span><span style="color: black;">&#93;</span>.<span style="color: black;">firstChild</span>.<span style="color: black;">toxml</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">22</span>:-<span style="color: #ff4500;">7</span><span style="color: black;">&#93;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #808080; font-style: italic;"># content, uuid, time, method are now available for further use.</span></div></td></tr></tbody></table></div>
<p>最关键的代码，只有几行而已。省掉了原来长篇累牍的coding。效率也错，我将自己近3000条饭否消息批量下载，共150余页，历时86秒。饭否服务器也很给面子，中途没有封锁我。</p>
<p><strong>总结一下</strong>：Xpath很适合在xml中定位各部分内容，定位精准，描述性极佳，是xml中的搜索利器。经常做xml解析的，不妨尝试一把。</p>
<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;">个人感言</h2>
<p>从纯手工正则表达式解析，到使用minidom解析，再到使用xpath，看似弯路，其实蛮有收获。从自己事必躬亲精确控制每一个细节（用手工作），再到借助工具实现一部分功能（手脑并用），再到完全用合适的工具来处理全部事情（用脑工作），似乎正是良性的发展路径。自豪地说，由于我已经使用过纯手工正则表达式的解析，即使现有的工具不适合我，我进可攻，退可守；我知道解析的细节，现有的工具（好看的封装而已嘛）骗不了我，即使它包装得再好，还是正则表达式在作引擎（曾经读过python处理xml的相关库文件的python代码，感谢开源）；从追求实现(it works!)到追求卓越的实现(the excellent solution)，也是进步的必然。我不是说使用正则式就低级——我从来没有说过诸如此类的话，不论是对正则表达式，还是对正则表达式的使用者；事实上，正则表达式一直是我的箧中飞刃；我爱正则表达式！——只是说，不同的工具在合适的场合，有不同的效用。不单要知道某种工具的缺点以便能够避其短，更重要的是要知道它的优点以便扬其长。这样才能从容地调兵遣将，手下无不可用之工具。</p>
<p>相关链接：</p>
<ul>
<li><a href="http://www.w3.org/TR/xpath">W3C关于XPath的介绍</a></li>
<li><a href="http://www.zvon.org/xxl/XPathTutorial/General/examples.html">xpath教程</a>，有中文版，图文并茂，清晰易懂。</li>
<li><a href="http://4suite.org">4suite</a>，python的xpath套件</li>
<li><a href="http://search.cpan.org/~samtregar/Class-XPath-1.4/XPath.pm">perl其实也有xpath的</a>。未测试试。</li>
<li><a href="https://addons.mozilla.org/zh-CN/firefox/addon/1095">XPath Checker</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://iregex.org/blog/fanfou-message-extractor-from-minidom-to-xpath.html/feed</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>饭否消息析取之regex vs xml</title>
		<link>http://iregex.org/blog/fanfou-message-extractor-regex-vs-xml.html</link>
		<comments>http://iregex.org/blog/fanfou-message-extractor-regex-vs-xml.html#comments</comments>
		<pubDate>Wed, 08 Oct 2008 10:53:59 +0000</pubDate>
		<dc:creator>rex</dc:creator>
				<category><![CDATA[教程]]></category>
		<category><![CDATA[fanfou]]></category>
		<category><![CDATA[perl]]></category>
		<category><![CDATA[python]]></category>
		<category><![CDATA[regex]]></category>
		<category><![CDATA[xml]]></category>

		<guid isPermaLink="false">http://iregex.org/?p=33</guid>
		<description><![CDATA[页内导航： 能否只用官方的API来获取全部饭否消息？ 饭否消息结构 使用regex解析饭否消息 使用xml解析饭否消息 两相比较 相关阅读 批量导出饭否程序的方法很多，但是基本思路都是先将该网... ]]></description>
			<content:encoded><![CDATA[<p>页内导航：</p>
<ul>
<li><a href="#xiaochaqu"><strong>能否只用官方的API来获取全部饭否消息？</strong></a></li>
<li><a href="#饭否消息结构"><strong>饭否消息结构</strong></a></li>
<li><a href="#regex"><strong>使用regex解析饭否消息</strong></a></li>
<li><a href="#python"><strong>使用xml解析饭否消息</strong></a></li>
<li><a href="#compare"><strong>两相比较</strong></a></li>
<li><a href="#xiangguan"><strong>相关阅读</strong></a></li>
</ul>
<p>
批量导出饭否程序的方法很多，但是基本思路都是先将该网页保存到本地，然后将有用的饭否消息析取出来。本文不讨论如何下载饭否网页了（使用迅雷、wget、curl等），重点讨论对于下载到本地的网页，如何将有用的饭否消息析取出来。
<p><span id="more-33"></span></p>
<blockquote style="border-left:2px solid #DDDDDD; margin:15px 30px 0 10px; padding-left:20px;">
<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;"><a href="#xiaochaqu"><strong><span style="color: #ff008c;">小插曲：能否只用官方的API来获取全部饭否消息？</span></strong></a></h2>
<p>您或许会提议为什么不使用饭否自身的API。是的，饭否的API更快捷方便，兼容性很强。只是，饭否官方只提供下载前20条饭否消息的API。如果纯粹使用饭否官方API来下载全部饭否消息的方法也不是没有，只是很邪恶：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span>true<span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; download <span style="color: #cc66cc;">20</span> messages via API<span style="color: #339933;">;</span><br />
&nbsp; &nbsp; store them<span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #000066;">delete</span> this <span style="color: #cc66cc;">20</span> messages via API<span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>
</p>
<p>一边下载一边删除，确实总能得到全部消息。删除了前面的20条，能保证后面的20条以新消息的面目出现。这在理论上是行得通的。但是我们需要的是英雄Heroes里Peter那样无损的复制方式，而不是Sylar那样的残忍的剪切方式，呵呵。既然官方的API有限制，我们就自己动手了。请继续阅读本文。</p>
</blockquote>
<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;">饭否消息结构</h2>
<p>打开一个饭否消息网页的源代码，例如本人的<br />
<a name="饭否消息结构"></a><a title=" 我爱正则表达式" href="http://fanfou.com/regex" target="_blank">http://fanfou.com/regex/p.1</a>（其实http://fanfou.com/regex是http://fanfou.com/regex/p.1的快捷方式。这里使用完整的路径，以便体现其一般性。），观察可见，有用的饭否消息在这个框架里面：（代码较长，阅读请点击展开）</p>
<div class="codecolorer-container xml mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;height:300px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br />17<br />18<br />19<br />20<br />21<br />22<br />23<br />24<br />25<br />26<br />27<br />28<br />29<br />30<br />31<br />32<br />33<br />34<br />35<br />36<br />37<br />38<br />39<br />40<br />41<br />42<br />43<br />44<br />45<br />46<br />47<br /></div></td><td><div class="xml codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"> <br />
<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;ol<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;li<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;span</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;content&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 代码非抄不能懂也。<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/span<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;span</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;stamp&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;a</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;time&quot;</span> <span style="color: #000066;">title</span>=<span style="color: #ff0000;">&quot;2008-10-03 12:07&quot;</span> <span style="color: #000066;">href</span>=<span style="color: #ff0000;">&quot;/statuses/QD6qHiqUbeE&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 2008-10-03 12:07<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/a<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;span</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;method&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 通过 <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;a</span> <span style="color: #000066;">href</span>=<span style="color: #ff0000;">&quot;http://del.icio.us/fanfou/API%E5%BA%94%E7%94%A8&quot;</span> <span style="color: #000066;">target</span>=<span style="color: #ff0000;">&quot;_blank&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; API<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/a<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/span<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/span<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/li<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
<br />
&nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;li<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;span</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;content&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 向自由的身心致敬！ - 早嗷嗷也盼~晚安安也盼~望穿安安双眼~~怎知道今日里打土匪进深山自己的队伍来哎到嗷~面安前安呐啊啊啊啊啊~~~ <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;a</span> <span style="color: #000066;">href</span>=<span style="color: #ff0000;">&quot;http://fanfou.com/linkto/aHR0cDovL3d3dy5kb3ViYW4uY29tL2V2ZW50LzEwMjczNDg3Lw&quot;</span> <span style="color: #000066;">target</span>=<span style="color: #ff0000;">&quot;_blank&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; http://www.douban.com/event/10273487/<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/a<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/span<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;span</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;stamp&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;a</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;time&quot;</span> <span style="color: #000066;">title</span>=<span style="color: #ff0000;">&quot;2008-10-06 14:07&quot;</span> <span style="color: #000066;">href</span>=<span style="color: #ff0000;">&quot;/share/bd96z1U-gHw&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 2008-10-06 14:07<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/a<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;span</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;method&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 通过<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;a</span> <span style="color: #000066;">href</span>=<span style="color: #ff0000;">&quot;http://help.fanfou.com/share_button.html&quot;</span> <span style="color: #000066;">target</span>=<span style="color: #ff0000;">&quot;_blank&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 饭否分享<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/a<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/span<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/span<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/li<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
<br />
&nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;li<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;span</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;content&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;a</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;photo&quot;</span> <span style="color: #000066;">href</span>=<span style="color: #ff0000;">&quot;http://fanfou.com/photo/8JsezhHM_VU&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;img</span> <span style="color: #000066;">src</span>=<span style="color: #ff0000;">&quot;http://photo.fanfou.com/m0/00/19/e2_36807.jpg&quot;</span> <span style="color: #000066;">alt</span>=<span style="color: #ff0000;">&quot;caixinceshi - no description&quot;</span> <span style="color: #000000; font-weight: bold;">/&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/a<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 上传了新照片：caixinceshi - no description<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/span<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;span</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;stamp&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;span</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;time&quot;</span> <span style="color: #000066;">title</span>=<span style="color: #ff0000;">&quot;2008-10-03 11:33&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 2008-10-03 11:33<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/span<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;span</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;method&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 通过<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;a</span> <span style="color: #000066;">href</span>=<span style="color: #ff0000;">&quot;http://help.fanfou.com/mobile_mms.html&quot;</span> <span style="color: #000066;">target</span>=<span style="color: #ff0000;">&quot;_blank&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 彩信<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/a<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/span<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/span<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/li<span style="color: #000000; font-weight: bold;">&gt;</span></span></span><br />
&nbsp; &nbsp; #更多的<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;li<span style="color: #000000; font-weight: bold;">&gt;</span></span></span>...<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/li<span style="color: #000000; font-weight: bold;">&gt;</span></span></span>条目，每页最多20条。<br />
<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/ol<span style="color: #000000; font-weight: bold;">&gt;</span></span></span></div></td></tr></tbody></table></div>
<p>Tips：在分析饭否源代码时，饭否消息全在一行，不便于阅读。您可以拷贝所需要的代码（注意前后结构的匹配呼应）到vim中，执行<tt class="string">:%s/&gt;/&gt;\r/g</tt>(将每个&gt;后面加上一个换行符)，再按<tt class="string">ggvG</tt>全选，按<tt class="string">=</tt>格式代码，所有的代码就成了漂亮的缩进格式，便于阅读了。</p>
</p>
<p><a name="regex"><br />
<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;">使用regex解析饭否消息</h2>
<p> </a></p>
<p>下面是使用regex来解析饭否消息的代码（直接拷贝自本人原来的perl抓饭程序。）</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #b1b100;">my</span> <span style="color: #0000ff;">$ffmsg</span><span style="color: #339933;">=</span><span style="color: #000066;">qr</span><span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #009999;">&lt;li&gt;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;content&quot;</span><span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;">&#40;</span><span style="color: #339933;">.*?</span><span style="color: #009900;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;stamp&quot;</span><span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/(?:statuses|share)/([-_a-zA-Z0-9]{11})&quot;</span> class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;time&quot;</span> title<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;([-: 0-9]{16})&quot;</span><span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;">&#91;</span><span style="color: #339933;">^&lt;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">&lt;/</span>a<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;method&quot;</span><span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 通过<span style="color: #009900;">&#40;</span>网页<span style="color: #339933;">|</span><span style="color: #009900;">&#40;</span><span style="color: #339933;">?:</span>\<span style="color: #000066;">s</span><span style="color: #339933;">*&lt;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^&gt;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+&gt;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^&lt;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#40;</span><span style="color: #339933;">?:&lt;/</span>a<span style="color: #339933;">&gt;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;/</span>li<span style="color: #339933;">&gt;</span><br />
<span style="color: #ff0000;">' }xi;</span></div></td></tr></tbody></table></div>
</p>
<p>可以看出，使用正则表达式，能够比较真实地再现原网页代码的风貌。有几处小地方需要说明一下：</p>
<ul>
<li>在第一组小括号里，我使用了<tt class="regex">([^<]+?)</tt>来捕获消息正文（一条完整的消息可以分为：消息正文；发送时间；消息uuid例如QD6qHiqUbeE，发送方法，类型（彩信还是文本））。最初是使用<tt class="regex">.*?</tt>的。但是这样不精确，有时候两条消息竟然混合在一起。而<tt class="regex">([^<]+?)</tt>捕获的是从当前位置开始至下一个&lt;之前的所有内容。或许您会问，这不怕受到消息正文中可能出现的&lt;的影响吗？答案是：不会受到影响。因为饭否会把所有的&lt;以及其实有可能影响解析的字符，都转换成&lt;的形式了，因此它不影响解析。同时，<strong>使用精确的正则表达式有助于提高效率，让不匹配的正则式尽早失败。</strong></li>
<li><tt class="regex">(?:statuses|share)</tt>。这条正则表达式是用来捕获饭否的uuid。它不但能捕获以普通方法发布的消息（网页、短信、手机、API、IM工具等），还能捕获由“饭否分享”工具发布的消息。我不是很喜欢饭否分享这个工具。（或许改天有时间写篇文章，揭露它的缺点？）之所以把“饭否分享”消息和普通消息分开来说，是因为两者的结构是不一样的。</li>
<li>通过<tt class="regex">(网页|(?:\s*<[^>]+>)[^<]+(?:))</tt>这条正则式，既用了捕获型括号，又用了非捕获型括号。使用后者，能有效地避免程序太复杂，便于按序号引用（$1,$2等，如果越多则越混乱，修改正则式后，更是乱成一团遭），还能节省内存（如果程序中捕获了太多的内容，而不及时释放，或许会占尽资源。毕竟不是只捕获几十字节。要考虑到饭否用户或许有近十万条的饭否消息。指的是<a href="http://fanfou.com/appleice">苹果流冰</a>这样的“万玻南痨话”）</li>
<li><tt class="regex">xi</tt>选项：<tt class="regex">x</tt>是为了使用忽略空白字符和允许注释；<tt class="regex">i</tt>选项是忽略大小写。</li>
</ul>
<p>使用正则表达式来析取饭否消息文本，需要考虑的细节很多。一处不细致，程序运行起来就会给你难看。饭否彩信的格式就略过不分析了。道理相同，点到为止。</p>
</p>
<p><a name="python"><br />
<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;">使用xml解析饭否消息</h2>
<p></a></p>
<p>再来看一下在python下，使用xml来解析饭否消息。注：该程序参考了<a href="http://www.happysky.org/" target="_blank"><strong><span style="color: #ff008c;">ppip</span></strong</a>的<a href="http://code.google.com/p/pyfan/" target="_blank">pyfan</a>程序。<br />
 </p>
<div class="codecolorer-container python mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br />17<br />18<br />19<br /></div></td><td><div class="python codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">xml</span>.<span style="color: black;">dom</span> <span style="color: #ff7700;font-weight:bold;">import</span> minidom, Node <span style="color: #808080; font-style: italic;">#引人解析工具：xml小马驹！</span><br />
node = minidom.<span style="color: black;">parse</span><span style="color: black;">&#40;</span><span style="color: #dc143c;">urllib2</span>.<span style="color: black;">urlopen</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;http://fanfou.com/zhasm/p.1&quot;</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span><br />
<span style="color: #808080; font-style: italic;">#抓取页面http://fanfou.com/zhasm/p.1 的全部内容到变量node中</span><br />
l = node.<span style="color: black;">getElementsByTagName</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;ol&quot;</span><span style="color: black;">&#41;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span><span style="color: black;">&#93;</span><br />
<span style="color: #808080; font-style: italic;">#将饭否消息部分内容保存到变量l中</span><br />
<span style="color: #ff7700;font-weight:bold;">for</span> c <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">range</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">0</span>, number<span style="color: black;">&#41;</span>:<br />
&nbsp; &nbsp; <span style="color: #808080; font-style: italic;"># 时间</span><br />
&nbsp; &nbsp; <span style="color: #ff7700;font-weight:bold;">if</span> l.<span style="color: black;">childNodes</span><span style="color: black;">&#91;</span>c<span style="color: black;">&#93;</span>.<span style="color: black;">hasAttribute</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;class&quot;</span><span style="color: black;">&#41;</span>:<br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #ff7700;font-weight:bold;">continue</span><br />
&nbsp; &nbsp; content = <span style="color: black;">&#40;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #808080; font-style: italic;">#时间:</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; l.<span style="color: black;">childNodes</span><span style="color: black;">&#91;</span>c<span style="color: black;">&#93;</span>.<span style="color: black;">childNodes</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">5</span><span style="color: black;">&#93;</span>.\<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; firstChild.<span style="color: black;">getAttribute</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;title&quot;</span><span style="color: black;">&#41;</span>,<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #808080; font-style: italic;">#消息正文 :</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; childNodes<span style="color: black;">&#91;</span>c<span style="color: black;">&#93;</span>.<span style="color: black;">childNodes</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span><span style="color: black;">&#93;</span>.<span style="color: black;">toxml</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">22</span>:-<span style="color: #ff4500;">7</span><span style="color: black;">&#93;</span>,<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #808080; font-style: italic;">#uuid</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; l.<span style="color: black;">childNodes</span><span style="color: black;">&#91;</span>c<span style="color: black;">&#93;</span>.<span style="color: black;">childNodes</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">5</span><span style="color: black;">&#93;</span>.<span style="color: black;">firstChild</span>.\<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; getAttribute<span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;href&quot;</span><span style="color: black;">&#41;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">10</span>:<span style="color: black;">&#93;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: black;">&#41;</span></div></td></tr></tbody></table></div>
<p>在xml文件中，前后呼应的标签，成了鲜活的特征，这些特征可以被xml解析函数很容易地辨识出来，并提取出所需内容。</p>
<ul>
<li><strong>childNodes[c].childNodes[0].toxml()[22:-7]</strong>：这条语句的意思是，对于每一条饭否消息（childNodes[c]），其消息内容的第一个节点（childNodes[0]），截取其第23字节到倒数第7字节的内容。它是指哪一段呢？其实就是每一对&lt;span class=&#8221;content&#8221;&gt;&#8230;&lt;/span&gt;之间点号所示的内容。</li>
<li>每条消息的发送时间、正文、uuid，保存在tuple中。</li>
</ul>
<p>取得了内容之后，至于之后的煎炒烹炸，就悉听尊便了。</p>
<p>值得一提的是，本人在大量下载饭否消息时，不止一次遇到过饭否页面无法访问的情况。问了饭否郭万怀，答曰为了减轻服务器负载，每个IP地址下每分钟允许访问100个页面。超过此数就会自动屏蔽。我测试的结果是少于100页。比较靠谱的间隔是，每析取一页，sleep(15)。是有些慢了。没办法。当然，也有人说，执行本人以前写的抓饭程序，一次下载几百页，并没有遇到当机情况。那我只能说是您的RP高、运气好了。</p>
</p>
<p><a name="compare"><br />
<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;">两者比较</h2>
<p></a> </p>
<p>个人认为，xml与regex相比，有如下特点：</p>
<ul>
<li><strong>通用性：</strong>xml具有通用性，不单单能解析饭否消息，其它符合规则的html文本，同样能够较少地改动代码，即可解析；而正则表达式则具有专用性，不能放之四海而皆准。当饭否的界面、框架有微调时，估计使用正则表达式解析的工具首先倒下。</li>
<li><strong>可读性：</strong>有人说perl是只写语言，regex尤甚。这是在说perl或regex代码在编写时性之所至，酣畅淋漓，执行也很高效。只是，如果代码格式混乱且无注释文档的话，隔数日、数月再读，仿佛读天书一般。而使用xml库来解析的python语言，则由于代码格式整齐，库函数见名知意，因而具有较强的可读性。这样说，总体是这样。不过我们可以尽可能把代码（即使是perl或regex的）写的整齐已读，尤其是考虑到perl支持<tt class="regex">/x</tt>选项。</li>
<li><strong>效率：</strong>良好编译的正则式，其执行效率应该优于xml解析。但是，使用xml能够节省编程时间；使用正则式牺牲一部分的编程时间，理论上能提高一点点效率。有兴趣的读者可以编写一段程序，循环个成千上万次，比较一下平均时间。</li>
</ul>
<p>
写到这里，对照金庸先生在《鹿鼎记》第五章：“金戈运启驱除会，玉匣书留想象间”两种武功的比较，颇有意味：<br />
“大慈大悲千叶手”招式太多，记起来麻烦。而“八卦游龙掌”只有八八六十四式，但反复变化，尽可敌得住千叶手。那么哪一门功夫厉害些？这两门都是上乘掌法，说不上哪一门功夫厉害。谁的功夫深，用得巧妙，谁就胜了。
<p>以本文来看，regex就相当于是大慈大悲千叶手了，需要留意的细节太多；xml方式呢，就相当于只有八八六十四式的“八卦游龙掌”。两种工具都很有用。</p>
</p>
<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;">呼吁官方提供更多功能</h2>
<p>离题了。这里顺便发发牢骚而已，与xml、regex无关。我不止一次地在饭否和本人blog中抱怨，使用上面这足粗笨的方法下载、解析，是最无奈的应用。最便捷的方式，应该是官方提供批量导出程序，只要执行一条数据库查询导出即可实现我们辛辛苦苦半天才能以变通的方式实现的功能。或许是饭否官方的人员都在忙着增强和美化海内吧，饭否自生自长，长时间没有更新，任凭jiwai.de、zuosa等推出一项又一项的新功能。 </p>
</p>
<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;">扩展</h2>
<p>本文的思路，对twitter同样适用。但是twitter越来越慢了。有一段时间好像还不支持查看历史页面。</p>
</p>
<p><a name="xiangguan"><br />
<h2 style="background-color:#99CC00; font-size:14px; padding-bottom:3px; padding-left:10px; padding-top:3px;  line-height:1.5em; margin:1.5em 0 1em;">相关阅读</h2>
<p></a></p>
<ul>
<li><a href="http://iregex.org/blog/fanfou-private-message-format-analysis.html" target="_blank">饭否私信格式分析</a></li>
<li><a href="http://zhasm.com/blog/fanfou-msg-grabber-limitation-and-suggestion-on-sharing-msg.html">关于饭否消息打包下载的限制以及对于饭否分享功能的建议</a></li>
<li><a href="http://zhasm.com/blog/about-my-fanfou-applications.html">关于本人编写的饭否应用的三言两语</a></li>
<li><a href="http://zhasm.com/blog/comments-on-fanfou.html">饭否，尚能饭否？</a></li>
<li><a href="http://zhasm.com/blog/uuid-in-twitter-and-fanfou.html">uuid in twitter and fanfou</a></li>
<li><a href="http://zhasm.com/blog/fanfou-message-grabber.html">批量抓饭脚本：一次性打包输出自己全部的饭否消息！</a></li>
<li><a href="http://zhasm.com/blog/fanfou-vs-twitter-base64-vs-tinyurl.html">fanfou vs twitter, base64 vs tinyurl?</a></li>
</ul>
<p><span style="color: #ffffff;">验证码：BANG1F79A9FAD20225BEA7FE397AXIANGUO e8da37692b5b030cbefb9956e3bdb9cc</span></p>
]]></content:encoded>
			<wfw:commentRss>http://iregex.org/blog/fanfou-message-extractor-regex-vs-xml.html/feed</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
		<item>
		<title>探索匹配中文的正则表达式</title>
		<link>http://iregex.org/blog/exploration-on-regular-rexpressions-that-match-chinese.html</link>
		<comments>http://iregex.org/blog/exploration-on-regular-rexpressions-that-match-chinese.html#comments</comments>
		<pubDate>Sat, 23 Aug 2008 16:22:29 +0000</pubDate>
		<dc:creator>rex</dc:creator>
				<category><![CDATA[教程]]></category>
		<category><![CDATA[chinese]]></category>
		<category><![CDATA[regex]]></category>
		<category><![CDATA[unicode]]></category>
		<category><![CDATA[utf8]]></category>
		<category><![CDATA[正则表达式]]></category>

		<guid isPermaLink="false">http://iregex.org/?p=31</guid>
		<description><![CDATA[按：本文使用的RegexBuddy为3.1.0（完全）版，并非最新版3.1.1（截至2008.08.23）。需要该版本的请在这篇文章后留言。 注：参考www.regular-expressions.info的风格，更新了本模板的style.css文件，加入了与... ]]></description>
			<content:encoded><![CDATA[<blockquote style="border-left:2px solid #DDDDDD; margin:15px 30px 0 10px; padding-left:20px;">
<p>按：本文使用的RegexBuddy为3.1.0（完全）版，并非最新版3.1.1（截至2008.08.23）。需要该版本的请在<a href="http://iregex.org/blog/regexbuddy.html" target="_blank"><font color="#ff008c">这篇</font></a>文章后留言。</p>
<p>注：参考<a href="http://www.regular-expressions.info" target="_blank">www.regular-expressions.info</a>的风格，更新了本模板的style.css文件，加入了与正则式代码相关的格式： </p>
<ul>
<li><strong>正则式</strong>格式举例：<tt class="regex">[a-z]+@[a-z]+?\.[a-z]+</tt> </li>
<li><strong>匹配</strong>格式举例：<tt class="match">pig@animals.com</tt>和<tt class="match">chicken@birds.com</tt> </li>
<li><strong>普通文本</strong>格式举例：<tt class="string">这是一些普通文本。hello regex world. pig@animals.com和chicken@birds.com</tt> </li>
</ul>
<p><span id="more-31"></span></p>
<p>可以这样使用：在字符串<tt class="string">这是一些普通文本。hello regex world. pig@animals.com和chicken@birds.com</tt>使用正则式<tt class="regex">[a-z]+@[a-z]+?\.[a-z]+</tt>加以匹配，得到的结果为：<tt class="match">pig@animals.com</tt>和<tt class="match">chicken@birds.com</tt>。 </p>
</blockquote>
<p><strong>极端粗放型</strong>：点号其实是近乎万能的，可以匹配任何字符，限制只在于换行符的匹配上。匹配中文自然不在话下。作为可有可无的背景符，一个<tt class="regex">.*</tt>就能匹配掉包括中文在内的全部字符。这当然是一种极端的情况，因为这样显示不出中文字符串的特性。这不是本文要探讨的。</p>
<p><strong>极端集约型</strong>：如果搜索特定文本，例如在<tt class="string">一二三四五六七八九十拾佰百千仟万亿</tt>中匹配<tt class="regex">十拾</tt>， 直接使用m/<tt class="regex">十拾</tt>/就能搞定。这同样不是本文要探讨的。与<tt class="regex">\w</tt>能匹配英文字母一样，本文想找的是能够匹配所有汉字，而不匹配其它文本的一种简写方式。 </p>
<p><strong>普适型型</strong>：由于汉字属于Unicode，我们就从unicode里面找。在<a href="http://unicode.org/reports/tr18/" target="_blank">Unicode Regular Expressions</a>，列出了unicode的许多种表达方式。搜索chinese，找到如下一行：</p>
<table width="400" border="1" cellpadding="2" cellspacing="1" unselectable="on">
<tbody>
<tr>
<td  valign="top" width="200">Writing Systems</td>
<td  valign="top" width="200">Blocks</td>
</tr>
<tr>
<td  valign="top" width="200">&#8230;</td>
<td  valign="top" width="200">&#8230;</td>
</tr>
<tr>
<td  valign="top" width="200">Chinese</td>
<td  valign="top" width="200">CJK Unified Ideographs, CJK Unified Ideographs Extension A, CJK Compatibility Ideographs, CJK Compatibility Forms, Enclosed CJK Letters and Months, Small Form Variants, Bopomofo, Bopomofo Extended</td>
</tr>
</tbody>
</table>
<p>关于CJK的含义，是指中日韩统一表意文字（Chinese Japanese Korean Unified Ideographs），可以参考<a href="http://baike.baidu.com/view/628156.html" target="_blank">百度释义</a>，或<a href="http://en.wikipedia.org/wiki/CJK" target="_blank">wiki</a>词条。</p>
<p>再查了一下<a href="http://www.regular-expressions.info/" target="_blank">regular expressions</a>,查到其<a href="http://www.regular-expressions.info/unicode.html" target="_blank">unicode</a>一节有这样的内容：
</p>
<blockquote style="border-left:2px solid #DDDDDD; margin:15px 30px 0 10px; padding-left:20px;"><p><tt class="regex">\p{InCJK_Unified_Ideographs}</tt>: U+4E00..U+9FFF </p></blockquote>
<p>
看到这里，我想起了以前写的<a href="http://iregex.org/blog/regular-expressions-to-match-chinese-username-in-asp.html" target="_blank">《匹配用户名的asp正则表达式(包括中文)》</a>一文中，提到的中文匹配为<tt class="regex">[\u4e00-\u9fa5]</tt>，原来是有其对应的速记方式的，虽然两者有最后一组字符的差异。看附图可见U+9fa5，最后一个汉字的模样。<img src="http://i3.6.cn/cvbnm/80/3c/69/ac41d1186fde1c67bf7cef334bc6a0c7.jpg" style="border: 1px solid rgb(255, 255, 255); margin: 0px 10px 10px; clear: both; padding-left: 0px; " alt="我爱正则表达式｜在RegexBuddy中如何使用正则表达式匹配中文字符｜http://iregex.org" /> 此序列的第一位，U+4e00，是汉字<tt class="string">一</tt>。
</p>
<p><strong>自定义</strong>：到目前为止，相当于给汉字找到了官方的身份和说法，使用<tt class="regex">\p{InCJK_Unified_Ideographs}</tt>就能匹配所有的中文字符。我们其实也可以将一些重复出现的东西，封装起来，以备使用。例如，对于阿拉伯数字，我们有<tt class="regex">\d</tt>可以用。对于中文数字一二三四等等，我们有没有办法呢？</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #0000ff;">$zh_digit</span><span style="color: #339933;">=</span><span style="color: #009966; font-style: italic;">qr/一|二|三|四|五|六|七|八|九|十|零|〇|百|千|万|亿|佰|仟|壹|贰|叁|肆|伍|陆|柒|捌|玖|拾/</span><span style="color: #339933;">;</span><br />
<br />
<span style="color: #0000ff;">$str</span><span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;人民币五十一万零三百元整。大写：伍拾壹万零三佰元整。&quot;</span><span style="color: #339933;">;</span><br />
<span style="color: #b1b100;">while</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">$str</span> <span style="color: #339933;">=~</span> <span style="color: #000066;">s</span><span style="color: #339933;">/</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#40;</span><span style="color: #339933;">?:</span><span style="color: #0000ff;">$zh_digit</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">//</span><span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #000066;">print</span> <span style="color: #0000ff;">$1</span><span style="color: #339933;">.</span><span style="color: #ff0000;">&quot;<span style="color: #000099; font-weight: bold;">\n</span>&quot;</span><span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>
</p>
<p>
<img src="http://i3.6.cn/cvbnm/6f/3d/c2/f974a15dbf6a2ceed6c6744961f39b27.jpg" src="http://i3.6.cn/cvbnm/80/3c/69/ac41d1186fde1c67bf7cef334bc6a0c7.jpg" style="border: 1px solid rgb(255, 255, 255); margin: 0px 10px 10px; clear: both; padding-left: 0px; " alt="我爱正则表达式｜在RegexBuddy中如何使用正则表达式匹配中文字符｜http://iregex.org" />
</p>
<p>其输出结果见附图。</p>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">结论</h3>
<p>可以使用<tt class="regex">\p{InCJK_Unified_Ideographs}</tt>匹配任意中文字符。在不支持该种标记方式时，也可以使用<tt class="regex">[\u4e00-\u9fa5]</tt>加以匹配。</p>
<p>关于文正则表达式，我觉得尚未穷其奥秘。以前在linux（utf8编码）下，编写scim输入平台的郑码码表时，匹配中文所使用的正则表达式为<tt class="regex">[\x80-\xff]{3}</tt>，也能很好地工作。请参阅此文：<a href="http://zhasm.com/blog/longwen-zhengma-ime-table-in-scim-format.html" target="_blank" title="我爱正则表达式｜在RegexBuddy中如何使用正则表达式匹配中文字符｜http://iregex.org">龙文郑码码表 for scim</a>。其原理我尚不清楚，留待之后有时间研究。如有知情者，也请不吝赐教，先行谢过。</p>
]]></content:encoded>
			<wfw:commentRss>http://iregex.org/blog/exploration-on-regular-rexpressions-that-match-chinese.html/feed</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>《精通正则表达式》视频教程提供下载</title>
		<link>http://iregex.org/blog/mastering-regular-expressions-vedio-tutorial-download.html</link>
		<comments>http://iregex.org/blog/mastering-regular-expressions-vedio-tutorial-download.html#comments</comments>
		<pubDate>Sun, 17 Aug 2008 04:02:35 +0000</pubDate>
		<dc:creator>rex</dc:creator>
				<category><![CDATA[教程]]></category>
		<category><![CDATA[newbie]]></category>
		<category><![CDATA[regex]]></category>
		<category><![CDATA[正则式]]></category>
		<category><![CDATA[正则表达式]]></category>

		<guid isPermaLink="false">http://iregex.org/?p=28</guid>
		<description><![CDATA[偶然从网上找到该教程，下载后觉得不错，可以作为《精通正则表达式》的番外篇，共同学习。 关于此视频的讲师： 此视频的讲师为余晟先生。余先生是抓虾网高级顾问。毕业于东北师范大学... ]]></description>
			<content:encoded><![CDATA[<p>偶然从<a href="http://tieba.baidu.com/f?kz=464065073" target="_blank">网上</a>找到该教程，下载后觉得不错，可以作为《<a href="http://www.douban.com/subject/2154713/" target="_blank">精通正则表达式</a>》的番外篇，共同学习。</p>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">关于此视频的讲师：</h3>
<p>此视频的讲师为<a href="http://www.luanxiang.org/blog/" target="_blank">余晟</a>先生。余先生是抓虾网高级顾问。毕业于东北师范大学，主修计算机，辅修中文。现居北京。曾任高级程序员、技术经理；从事过大量文本解析和数据抽取的工作。对程序语言、算法、数据库和敏捷开发都有兴趣，译有《精通正则表达式》(第3版)一书。</p>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">关于此视频</h3>
<p>此视频分为5讲，每讲30分钟左右，内容深入浅出，适合以下受众：</p>
<ul>
<li>对正则式感兴趣的人；</li>
<li>对正则式不感兴趣的人；</li>
<li>正则式初学者，想入门；</li>
<li>正则式有所成者，想提高。</li>
</ul>
<p>当然，如果能静下心来，通读《<a href="http://www.douban.com/subject/2154713/" target="_blank">精通正则表达式</a>》原书，并亲自动手尝试，效果更为显著。<span id="more-28"></span></p>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">目录及下载：</h3>
<p>视频文件（avi格式）已经使用<a href="http://www.7-zip.org/" target="_blank">7-zip</a>压缩，使其总尺寸从784Mb减小到74.7Mb。您需要使用支持7-zip的解压软件才能打开。</p>
<p>上传空间在<a href="http://www.mediafire.com" target="_blank">mediafire</a>。在网络封锁日益严峻的大环境下，您或许需要使用代那个理才能访问。我不敢保证此文件址长时有效。需要下载的请抓紧时间。</p>
<table border="1" cellspacing="1" cellpadding="2" width="385">
<tbody>
<tr>
<td width="43" align="middle">章节</td>
<td width="254" align="middle" valign="top">内容</td>
<td width="42" align="middle">大小（Mb）</td>
<td width="39" align="middle">链接</td>
</tr>
<tr>
<td width="46" align="middle">第一讲</td>
<td width="256" valign="top"><a href="http://tu.6.cn/pic/show/id/353660"><img src="http://i3.6.cn/cvbnm/38/97/2e/af092f3b004368b914f828e87bf0a700.jpg" alt="" /></a></td>
<td width="44" align="middle">15.5</td>
<td width="41" align="middle"><a title="我爱正则表达式｜精通正则式视频教程｜资源下载" href="http://www.mediafire.com/file/zgdlmjrryn1" target="_blank"><del datetime="2008-11-04T13:59:50+00:00">点此下载</del></a></td>
</tr>
<tr>
<td width="47" align="middle">第二讲</td>
<td width="256" valign="top"><a href="http://tu.6.cn/pic/show/id/353661"><img src="http://i3.6.cn/cvbnm/6b/e9/a0/6ed09224a2cf26678f5b12b4f5279178.jpg" alt="" /></a></td>
<td width="45" align="middle">13.1</td>
<td width="42" align="middle"><a title="我爱正则表达式｜精通正则式视频教程｜资源下载" href="http://www.mediafire.com/file/rhjhdvzjrna" target="_blank"><del datetime="2008-11-04T13:59:50+00:00">点此下载</del></a></td>
</tr>
<tr>
<td width="46" align="middle">第三讲</td>
<td width="256" valign="top"><a href="http://tu.6.cn/pic/show/id/353662"><img src="http://i3.6.cn/cvbnm/a2/c2/b4/92dd6a034a2c806929956c85f55bb182.jpg" alt="" /></a></td>
<td width="45" align="middle">16.6</td>
<td width="43" align="middle"><a title="我爱正则表达式｜精通正则式视频教程｜资源下载" href="http://www.mediafire.com/file/uhsktmtle6u" target="_blank"><del datetime="2008-11-04T13:59:50+00:00">点此下载</del></a></td>
</tr>
<tr>
<td width="46" align="middle">第四讲</td>
<td width="256" valign="top"><a href="http://tu.6.cn/pic/show/id/353663"><img src="http://i3.6.cn/cvbnm/3e/d7/f6/fcc2d994ed9ae134c8cf6d51a0beaeff.jpg" alt="" /></a></td>
<td width="45" align="middle">15.3</td>
<td width="43" align="middle"><a title="我爱正则表达式｜精通正则式视频教程｜资源下载" href="http://www.mediafire.com/file/8inm2eqwnrk" target="_blank"><del datetime="2008-11-04T13:59:50+00:00">点此下载</del></a></td>
</tr>
<tr>
<td width="46" align="middle">第五讲</td>
<td width="256" valign="top"><a href="http://tu.6.cn/pic/show/id/353664"><img src="http://i3.6.cn/cvbnm/21/48/84/f48278bc22bb44e4db5e036bece56436.jpg" alt="" /></a></td>
<td width="45" align="middle">13.9</td>
<td width="43" align="middle"><a title="我爱正则表达式｜精通正则式视频教程｜资源下载" href="http://www.mediafire.com/file/mphmtaojmlh" target="_blank"><del datetime="2008-11-04T13:59:50+00:00">点此下载</del></a></td>
</tr>
<tr>
<td width="46" align="middle">源代码</td>
<td width="256" valign="top"></td>
<td width="45" align="middle">16.9Kb</td>
<td width="43" align="middle"><a href="http://www.mediafire.com/?bzmntyv3z5z" target="_blank"><del datetime="2008-11-04T13:59:50+00:00">点此下载</del></a></td>
</tr>
</tbody>
</table>
<p><strong><font color="#FF008c">2009.04.07更新：</font></strong><br />
请到此下载：<a href="http://regex.me/thread-6-post-9.html" target="_blank" title="正则表达式论坛|精通正则表达式视频教程">正则表达式论坛</a>。</p>
]]></content:encoded>
			<wfw:commentRss>http://iregex.org/blog/mastering-regular-expressions-vedio-tutorial-download.html/feed</wfw:commentRss>
		<slash:comments>14</slash:comments>
		</item>
		<item>
		<title>匹配中文的正则表达式</title>
		<link>http://iregex.org/blog/regex-to-match-chinese.html</link>
		<comments>http://iregex.org/blog/regex-to-match-chinese.html#comments</comments>
		<pubDate>Mon, 02 Jun 2008 06:23:37 +0000</pubDate>
		<dc:creator>rex</dc:creator>
				<category><![CDATA[教程]]></category>
		<category><![CDATA[chinese]]></category>
		<category><![CDATA[python]]></category>
		<category><![CDATA[regex]]></category>
		<category><![CDATA[utf8]]></category>

		<guid isPermaLink="false">http://iregex.org/?p=14</guid>
		<description><![CDATA[以前在编写linux下的scim郑码码表时，就跟正则式的中文匹配问题打过交道。当时总结了这样一条经验，utf8编码格式下，中文正则式应该这样书写： 1&#91;\x80-\xff&#93;&#123;3&#125; 当然，这与语言无... ]]></description>
			<content:encoded><![CDATA[<p>以前在编写linux下的scim郑码码表时，就跟正则式的中文匹配问题打过交道。当时总结了这样一条经验，utf8编码格式下，中文正则式应该这样书写：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #009900;">&#91;</span><span style="color: #0000ff;">\x80</span><span style="color: #339933;">-</span><span style="color: #0000ff;">\xff</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#123;</span><span style="color: #cc66cc;">3</span><span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>
<p>当然，这与语言无关。在perl与python中，都是一样的。</p>
<p>现在，这条正则式又派上用场了。正在编写的一个小程序<a href="http://code.google.com/p/fanfoufans/wiki/MiniBlogsUpdater" target="_blank" title="一次输入，五处更新！同时更新twitter,海内，叽歪的，做啥，饭否的微博客。">MiniBlogs Updater</a>中，需要计算用户所输入的文字字数。因为中英文字符编码长度不一，如果直接使用python中的len()函数，它计算的是该字串的实际长度，一个中文字并非等同于一个英文字母的。因此，需要把中文字当成英文字母来处理。</p>
<p>我写了这样一条语句来处理：</p>
<div class="codecolorer-container python mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="python codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">length=<span style="color: #008000;">len</span><span style="color: black;">&#40;</span><span style="color: #dc143c;">re</span>.<span style="color: black;">sub</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'[<span style="color: #000099; font-weight: bold;">\x</span>80-<span style="color: #000099; font-weight: bold;">\x</span>ff]{3}'</span>,<span style="color: #483d8b;">'a'</span>,msg<span style="color: black;">&#41;</span><span style="color: black;">&#41;</span></div></td></tr></tbody></table></div>
<p>它的意思是，把所有的中文都替换成英文字母a，然后再统计字数。（只是统计而已，不修改源字串。）这条语句在windows下utf8文件中能够正常工作。</p>
<p>再分享两则与匹配中文的正则表达式有用的链接：</p>
<ul>
<li><a href="http://bbs.chinaunix.net/viewthread.php?tid=975358" target="_blank">常见中文正则表达式匹配结果比较</a></li>
<li><a href="http://bbs.chinaunix.net/viewthread.php?tid=907172" target="_blank">[分享]对各字符集编码范围的总结[更新日期2007-03-12]</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://iregex.org/blog/regex-to-match-chinese.html/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>饭否私信格式分析</title>
		<link>http://iregex.org/blog/fanfou-private-message-format-analysis.html</link>
		<comments>http://iregex.org/blog/fanfou-private-message-format-analysis.html#comments</comments>
		<pubDate>Sat, 31 May 2008 04:07:38 +0000</pubDate>
		<dc:creator>rex</dc:creator>
				<category><![CDATA[杂项]]></category>
		<category><![CDATA[fanfou]]></category>
		<category><![CDATA[perl]]></category>
		<category><![CDATA[regex]]></category>

		<guid isPermaLink="false">http://iregex.org/?p=13</guid>
		<description><![CDATA[URL 饭否私信分为两种，一种是我收到的私信，一种是我发出的私信。 我收到的私信：http://fanfou.com/privatemsg/p.(1-N) 我发出的私信：http://fanfou.com/privatemsg/sent/p.(1-N) 上面的地址中不含饭否ID；需要... ]]></description>
			<content:encoded><![CDATA[<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">URL</h3>
<p>饭否私信分为两种，一种是我收到的私信，一种是我发出的私信。</p>
<ul>
<li> 我收到的私信：http://fanfou.com/privatemsg/p.(1-N)</li>
<li> 我发出的私信：http://fanfou.com/privatemsg/sent/p.(1-N)</li>
</ul>
<p>上面的地址中不含饭否ID；需要cookie验证。</p>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">结束标志</h3>
<p>通过cookie验证后，可以使用数字获得对应页码的私信内容。什么时候是结束呢？假如您的收件箱有1000条私信，每页显示20条，那么当你您输入http://fanfou.com/privatemsg/p.51时，就得不到任何有效的内容了。作为程序，它是寻找如下标志：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #339933;">&lt;</span>ol class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;wa&quot;</span><span style="color: #339933;">&gt;</span>\<span style="color: #000066;">s</span><span style="color: #339933;">*&lt;/</span>ol<span style="color: #339933;">&gt;</span></div></td></tr></tbody></table></div>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">好友列表</h3>
<p>在页面代码中，每页都有一个“向XXX发送私信”的combox列表，条目以<font color="#ff0084">昵称+ID</font>组成。如果你的好友很多的话（500+），每条好友（昵称+ID）需要20字节（估算）的话，20*500=10K，大约需要多抓取10K的字节量。</p>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">收件箱饭否私信的结构</h3>
<p>收到的私信分为两种，一种是有回复信息的（回复原文:…），一种是没有回复的。先从简单的入手，看没有回复的。<br />
所有的私信都在<font color="#ff0084">&lt;ol class=&#8221;wa&#8221;&gt;…&lt;/ol&gt;</font>之内，以<font color="#ff0084">&lt;li&gt;&lt;/li&gt;</font>分隔</p>
<p>例如下面这一条，就是一则很规范的私信（与发件人相关的信息都使以正则式表示）：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #009999;">&lt;li&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot; title=&quot;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+&quot;</span> class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;avatar&quot;</span><span style="color: #339933;">&gt;&lt;</span>img src<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot; alt=&quot;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+&quot;</span> <span style="color: #339933;">/&gt;&lt;/</span>a<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; 来自<span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot;&gt;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+&lt;/</span>a<span style="color: #339933;">&gt;</span>：<br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;content&quot;</span><span style="color: #339933;">&gt;</span>没法比较啊<span style="color: #339933;">,</span>你得说个具体的值<span style="color: #339933;">,</span>比如<span style="color: #cc66cc;">100</span>条以下的算少<span style="color: #339933;">,</span><span style="color: #cc66cc;">1000</span>条以上的算多……<span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;stamp time&quot;</span> title<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;2008-05-30 17:25&quot;</span><span style="color: #339933;">&gt;</span>约 <span style="color: #cc66cc;">15</span> 小时前<span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;op&quot;</span><span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/privatemsg.reply/583520&quot;</span><span style="color: #339933;">&gt;</span>回复<span style="color: #339933;">&lt;/</span>a<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/privatemsg.del/583520&quot;</span> class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;post_act&quot;</span><span style="color: #339933;">&gt;</span>删除<span style="color: #339933;">&lt;/</span>a<span style="color: #339933;">&gt;&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
<span style="color: #339933;">&lt;/</span>li<span style="color: #339933;">&gt;</span></div></td></tr></tbody></table></div>
<p>其中，需要记录的信息有：</p>
<ul>
<li>发件人名字；</li>
<li>发件人ID；</li>
<li>私信内容；</li>
<li>时间；</li>
<li>私信ID；（便于作删除、回复处理）。</li>
</ul>
<p>根据以上需求，将上面的私信代码作处理：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #009999;">&lt;li&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/([^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot; title=&quot;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+)&quot;</span> class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;avatar&quot;</span><span style="color: #339933;">&gt;&lt;</span>img src<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot; alt=&quot;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+&quot;</span> <span style="color: #339933;">/&gt;&lt;/</span>a<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; 来自<span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot;&gt;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+&lt;/</span>a<span style="color: #339933;">&gt;</span>：<br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;content&quot;</span><span style="color: #339933;">&gt;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^&lt;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;stamp time&quot;</span> title<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;([^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot;&gt;[^&lt;]+&lt;/span&gt;<br />
&nbsp; &nbsp; &lt;span class=&quot;</span>op<span style="color: #ff0000;">&quot;&gt;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &lt;a href=&quot;</span><span style="color: #339933;">/</span>privatemsg<span style="color: #339933;">.</span>reply<span style="color: #339933;">/</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">\d</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot;&gt;回复&lt;/a&gt;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &lt;a href=&quot;</span><span style="color: #339933;">/</span>privatemsg<span style="color: #339933;">.</span>del<span style="color: #339933;">/</span><span style="color: #0000ff;">\d</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot; class=&quot;</span>post_act<span style="color: #ff0000;">&quot;&gt;删除&lt;/a&gt;<br />
&nbsp; &nbsp; &lt;/span&gt;<br />
&lt;/li&gt;</span></div></td></tr></tbody></table></div>
<p>从而得到：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #0000ff;">$1</span><span style="color: #339933;">=</span>fanfou ID<span style="color: #339933;">;</span><br />
<span style="color: #0000ff;">$2</span><span style="color: #339933;">=</span>fanfou name<span style="color: #339933;">;</span><br />
<span style="color: #0000ff;">$3</span><span style="color: #339933;">=</span>private msg<span style="color: #339933;">;</span><br />
<span style="color: #0000ff;">$4</span><span style="color: #339933;">=</span>msg <span style="color: #000066;">time</span><span style="color: #339933;">;</span><br />
<span style="color: #0000ff;">$5</span><span style="color: #339933;">=</span>msg ID<span style="color: #339933;">;</span></div></td></tr></tbody></table></div>
<p>再看一下包含“回复原文”的私信的结构(部分内容已作正则处理)：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #009999;">&lt;li&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/([^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot; title=&quot;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+)&quot;</span> class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;avatar&quot;</span><span style="color: #339933;">&gt;&lt;</span>img src<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot; alt=&quot;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+&quot;</span> <span style="color: #339933;">/&gt;&lt;/</span>a<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; 来自<span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot;&gt;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+&lt;/</span>a<span style="color: #339933;">&gt;</span>：<br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;content&quot;</span><span style="color: #339933;">&gt;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^&lt;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;stamp time&quot;</span> title<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;([^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot;&gt;[^&lt;]+&lt;/span&gt;<br />
&nbsp; &nbsp; &lt;span class=&quot;</span>op<span style="color: #ff0000;">&quot;&gt;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &lt;a href=&quot;</span><span style="color: #339933;">/</span>privatemsg<span style="color: #339933;">.</span>reply<span style="color: #339933;">/</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">\d</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot;&gt;回复&lt;/a&gt;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &lt;a href=&quot;</span><span style="color: #339933;">/</span>privatemsg<span style="color: #339933;">.</span>del<span style="color: #339933;">/</span><span style="color: #0000ff;">\d</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot; class=&quot;</span>post_act<span style="color: #ff0000;">&quot;&gt;删除&lt;/a&gt;<br />
&nbsp; &nbsp; &lt;/span&gt;<br />
&nbsp; &nbsp; &lt;p class=&quot;</span>pm<span style="color: #339933;">-</span>parent<span style="color: #ff0000;">&quot;&gt;回复原文: 有兴趣就有动力&lt;/p&gt;<br />
&lt;/li&gt;</span></div></td></tr></tbody></table></div>
<p>与前者相比，只是多了<font color="#ff0084">&lt;p class=&#8221;pm-parent&#8221;&gt;.*?&lt;/p&gt;</font>这一段。这是不足为虑的。只要整体加上<font color="#ff0084">?</font>这个强有力的正则符号，就能与上面的代码片段归纳到一起。两者结合合的代码如下：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #009999;">&lt;li&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/([^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot; title=&quot;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+)&quot;</span> class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;avatar&quot;</span><span style="color: #339933;">&gt;&lt;</span>img src<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot; alt=&quot;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+&quot;</span> <span style="color: #339933;">/&gt;&lt;/</span>a<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; 来自<span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot;&gt;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+&lt;/</span>a<span style="color: #339933;">&gt;</span>：<br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;content&quot;</span><span style="color: #339933;">&gt;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^&lt;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;stamp time&quot;</span> title<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;([^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot;&gt;[^&lt;]+&lt;/span&gt;<br />
&nbsp; &nbsp; &lt;span class=&quot;</span>op<span style="color: #ff0000;">&quot;&gt;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &lt;a href=&quot;</span><span style="color: #339933;">/</span>privatemsg<span style="color: #339933;">.</span>reply<span style="color: #339933;">/</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">\d</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot;&gt;回复&lt;/a&gt;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &lt;a href=&quot;</span><span style="color: #339933;">/</span>privatemsg<span style="color: #339933;">.</span>del<span style="color: #339933;">/</span><span style="color: #0000ff;">\d</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot; class=&quot;</span>post_act<span style="color: #ff0000;">&quot;&gt;删除&lt;/a&gt;&lt;/span&gt;<br />
&nbsp; &nbsp; (?:&lt;p class=&quot;</span>pm<span style="color: #339933;">-</span>parent<span style="color: #ff0000;">&quot;&gt;([^&lt;]+)&lt;/p&gt;)?<br />
&lt;/li&gt;</span></div></td></tr></tbody></table></div>
<p>得到的变量为：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #0000ff;">$1</span><span style="color: #339933;">=</span>fanfou ID<span style="color: #339933;">;</span><br />
<span style="color: #0000ff;">$2</span><span style="color: #339933;">=</span>fanfou name<span style="color: #339933;">;</span><br />
<span style="color: #0000ff;">$3</span><span style="color: #339933;">=</span>private msg<span style="color: #339933;">;</span><br />
<span style="color: #0000ff;">$4</span><span style="color: #339933;">=</span>msg <span style="color: #000066;">time</span><span style="color: #339933;">;</span><br />
<span style="color: #0000ff;">$5</span><span style="color: #339933;">=</span>msg ID<span style="color: #339933;">;</span><br />
<span style="color: #0000ff;">$6</span><span style="color: #339933;">=</span>parent msg<span style="color: #339933;">;</span><span style="color: #666666; font-style: italic;">#回复原文。</span></div></td></tr></tbody></table></div>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">发件箱饭否私信的结构</h3>
<p>抄代码：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #009999;">&lt;li&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/([^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot; title=&quot;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+)&quot;</span> class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;avatar&quot;</span><span style="color: #339933;">&gt;&lt;</span>img src<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot; alt=&quot;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+&quot;</span> <span style="color: #339933;">/&gt;&lt;/</span>a<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; 发给<span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot;&gt;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+&lt;/</span>a<span style="color: #339933;">&gt;</span>：<br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;content&quot;</span><span style="color: #339933;">&gt;</span>海内的像片是真的。<span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;stamp time&quot;</span> title<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;2008-05-28 20:24&quot;</span><span style="color: #339933;">&gt;</span><span style="color: #cc66cc;">2008</span><span style="color: #339933;">-</span>05<span style="color: #339933;">-</span><span style="color: #cc66cc;">28</span> <span style="color: #cc66cc;">20</span><span style="color: #339933;">:</span><span style="color: #cc66cc;">24</span><span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;op&quot;</span><span style="color: #339933;">&gt;&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/privatemsg.del/576827&quot;</span> class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;post_act&quot;</span><span style="color: #339933;">&gt;</span>删除<span style="color: #339933;">&lt;/</span>a<span style="color: #339933;">&gt;&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
<span style="color: #339933;">&lt;/</span>li<span style="color: #339933;">&gt;</span></div></td></tr></tbody></table></div>
<p>这与“我收到的私信”的结构完全一致，只是将原来的“来自”改为“发给”而已。</p>
<p>不出意外，带有“回复原文”的“我收到的私信”的结构是这样的：</p>
<div class="codecolorer-container perl mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br /></div></td><td><div class="perl codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #009999;">&lt;li&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/([^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #009900;">&#41;</span><span style="color: #ff0000;">&quot; title=&quot;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+)&quot;</span> class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;avatar&quot;</span><span style="color: #339933;">&gt;&lt;</span>img src<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot; alt=&quot;</span><span style="color: #009900;">&#91;</span><span style="color: #339933;">^</span><span style="color: #ff0000;">&quot;]+&quot;</span> <span style="color: #339933;">/&gt;&lt;/</span>a<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; 发给<span style="color: #339933;">&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+</span><span style="color: #ff0000;">&quot;&gt;[^&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">+&lt;/</span>a<span style="color: #339933;">&gt;</span>：<br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;content&quot;</span><span style="color: #339933;">&gt;</span>在自述部分显示的那个网上。<span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;stamp time&quot;</span> title<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;2008-05-29 17:00&quot;</span><span style="color: #339933;">&gt;</span><span style="color: #cc66cc;">2008</span><span style="color: #339933;">-</span>05<span style="color: #339933;">-</span><span style="color: #cc66cc;">29</span> <span style="color: #cc66cc;">17</span><span style="color: #339933;">:</span>00<span style="color: #339933;">&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>span class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;op&quot;</span><span style="color: #339933;">&gt;&lt;</span>a href<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;/privatemsg.del/579918&quot;</span> class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;post_act&quot;</span><span style="color: #339933;">&gt;</span>删除<span style="color: #339933;">&lt;/</span>a<span style="color: #339933;">&gt;&lt;/</span>span<span style="color: #339933;">&gt;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">&lt;</span>p class<span style="color: #339933;">=</span><span style="color: #ff0000;">&quot;pm-parent&quot;</span><span style="color: #339933;">&gt;</span>回复原文<span style="color: #339933;">:</span> 我也要试一试。<span style="color: #339933;">&lt;/</span>p<span style="color: #339933;">&gt;</span><br />
<span style="color: #339933;">&lt;/</span>li<span style="color: #339933;">&gt;</span></div></td></tr></tbody></table></div>
<p>我们从饭否私信代码上得到的信息就这些。遗憾的是，饭否私信中，关于“回复原文”是以明文内容形式出现，而不是以原私信ID的形式出现。后期处理时通过搜索功能解决此问题并非不能，只是如果饭否官方能够再将此功能完善的话，会省整理者不少力气。</p>
<p>饭否的私信源码分析完毕。至于如何读写cookie，如何写代码，如何以数据库的形式来管理下载的数据，是第二阶段的事情了。待我一一实现。</p>
]]></content:encoded>
			<wfw:commentRss>http://iregex.org/blog/fanfou-private-message-format-analysis.html/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>windows下的正则式工具介绍之二：powergrep</title>
		<link>http://iregex.org/blog/powergrep.html</link>
		<comments>http://iregex.org/blog/powergrep.html#comments</comments>
		<pubDate>Mon, 05 May 2008 08:18:09 +0000</pubDate>
		<dc:creator>rex</dc:creator>
				<category><![CDATA[软件]]></category>
		<category><![CDATA[powergrep]]></category>
		<category><![CDATA[regex]]></category>
		<category><![CDATA[regexbuddy]]></category>
		<category><![CDATA[正则式]]></category>
		<category><![CDATA[正则表达式]]></category>

		<guid isPermaLink="false">http://iregex.org/?p=7</guid>
		<description><![CDATA[上文介绍了RegexBuddy，本文介绍另一款windows下的正则式软件：PowerGREP，号称“The Most Powerful GREP Tool for Windows”，windows下最强大的GREP工具。看清楚了，是最强大，而非之一。与RegexBuddy一样，也是... ]]></description>
			<content:encoded><![CDATA[<p>上文介绍了RegexBuddy，本文介绍另一款windows下的正则式软件：PowerGREP，号称“The Most Powerful GREP Tool for Windows”，windows下最强大的GREP工具。看清楚了，是<font color="#ff0084">最强大</font>，而非<font color="#ff0084">之一</font>。与RegexBuddy一样，也是商业软件，其售价为US$149.00，合人民币1000有奇。如果说RegexBuddy是撰写正则式的贴心助手，那么PowerGREP则是应用正则式在文本文件中搜索替换的强大工具。现在我们看看，它究竟有什么功能敢号称<b>最强</b>。</p>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">基本界面</h3>
<p><a target="_blank" href="http://www.powergrep.com/screens/powergrep800.png"><img style="max-width: 800px;" src="http://www.powergrep.com/screens/powergrep320.png" /></a></p>
<p>点击可以看大图。另外，还有一组图片来自<a target="_blank" href="http://www.powergrep.com">powergrep</a>官网，附上了官网的部分介绍，以及个人评论。</p>
<ul>
<li>内容搜索图片，点<a target="_blank" href="http://www.powergrep.com/screens/powergrep800.png">这里</a>；<br />
在本抓图中，我搜索了<font color="#ff0084">c:\My Documents\My Web Sites</font>文件夹及其子目录下所有的html文件。我使用了一条正则表达式把搜索范围限定在HTML tag之内，使用另一条正则式在这些<span class="hl">标记中搜索所有的email地址。</p>
<p></span></li>
<li>搜索和替换，点<a target="_blank" href="http://www.powergrep.com/screens/replacepreview.png">这里</a>和<a target="_blank" href="http://www.powergrep.com/screens/replace.png">这里</a>；<br />
一个好用的功能是可以<font color="#ff0084">预览</font>结果而不是立即替换。匹配结果以黄色标出。双击匹配就能打开对应的文档并检验其内容。<br />
点击<font color="#ff0084">执行</font>后，颜色改变，表示已经实施替换。</p>
</li>
<li>收集信息和统计数据，点<a target="_blank" href="http://www.powergrep.com/screens/collect.png">这里</a>；<br />
本例是“检测Apache网络日志－－google search terms”的例子。本例使用的正则式在PowerGREP帮助文档中有详细讲解。</p>
</li>
<li>灵活的“撤消”历史记录，让你不再抓狂，点<a href="http://www.powergrep.com/screens/undo.png" target="_blank">这里</a>；<br />
在执行替换的同时，PowerGREP已经备份了原文件。只要你没有手动删除这些备份的文件，你可以随便撤消你做过的任何操作。世界上真有后悔药的呀。</p>
</li>
<li>搜索PDF文档，点<a target="_blank" href="http://www.powergrep.com/screens/pdf.png">这里</a>；<br />
PDF也能使用正则式进行搜索？当然了，你没有看错。只是，要确保PDF文档中你要搜索的内容是<font color="#ff0084">文字</font>而非<font color="#ff0084">图像</font>。也就是说，扫描版的PDF不享受此功能的哟。</p>
</li>
<li>在MS word 文档中搜索，点<a target="_blank" href="http://www.powergrep.com/screens/msword.png">这里</a>；<br />
这个功能也十分有用。我记得还有个东东叫<a target="_blank" href="http://www.viemu.com/">ViEmu for Word &amp; Outlook</a>，可以在word和outlook中模拟vim，当然可以使用正则式搜索替换了。不过，ViEmu一来也是收费软件（在2008年5月31日之前是79美刀，之后是99美刀），我还没有找到免费版本；二来其正则式是vim风格的，只习惯Perl风格的同学可能不太习惯。在google documents里也支持正则式搜索了，具体语法、风格尚未广泛测试。</p>
</li>
<li>在MS Excel中搜索，点<a target="_blank" href="http://www.powergrep.com/screens/excel.png">这里</a>；<br />
同样也是批量搜索、替换。不单单是对一个文档、一个sheet。</p>
</li>
<li>以16进制模式，在2进制文档中搜索，点<a target="_blank" href="http://www.powergrep.com/screens/binaryfiles.png">这里</a>；<br />
跟二进制编辑器界面类似，多了正则式批量搜索替换功能。</p>
</li>
<li>在zip压缩文档中搜索，点<a target="_blank" href="http://www.powergrep.com/screens/zip.png">这里</a>；<br />
把zip文件当作普通文件夹来搜索。很强大吧？</p>
</li>
<li>正则表达式序列，点<a target="_blank" href="http://www.powergrep.com/screens/sequence.png">这里</a>；<br />
大多数正则式工具一次只支持一条正则式的操作。而PowerGREP可以一次执行多条正则式！使用checkbox来进行多项选择。</p>
</li>
<li>定制颜色显示，点<a target="_blank" href="http://www.powergrep.com/screens/colors.png">这里</a>；<br />
该功能比较一般。除非软件中的颜色设置特傻，一般我是不会改变默认颜色搭配的。
</li>
</ul>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">功能演示</h3>
<p>PowerGREP官网还提供了一组flash做的demo，见下。</p>
<ul>
<li>使用正则式匹配email地址(2&#8217;47&#8221;)。点<a target="_blank" href="http://www.powergrep.com/demos/email.swf">这里</a>；</li>
<li>升级版权信息(3&#8217;38)。点<a target="_blank" href="http://www.powergrep.com/demos/copyright.swf">这里</a>；</li>
<li>与RegexBuddy的无缝链接(1&#8217;57&#8221;)，点这里；两个软件是亲兄弟，当然哥俩好啦！
</li>
<li>文件选择(3&#8217;08&#8221;)，点<a target="_blank" href="http://www.powergrep.com/demos/filesel.swf">这里</a>；PowerGREP提供了贴心的特性，来帮助你筛选需要的文档。</li>
<li>其它特性(8&#8217;37&#8221;)，点<a target="_blank" href="http://www.powergrep.com/demos/action.swf">这里</a>；总而言之，PowerGREP是功能强大。自己发掘吧！</li>
</ul>
<h3 style="color: #127ADB; font-size:14px; padding-bottom:3px; padding-top:3px; margin:1.5em 0 1em;">软件下载</h3>
<p> 目前其最新版为3.4.2，更新于2008年1月18日。其官网为<a href="http://www.powergrep.com/" target="_blank">www.powergrep.com</a>，可以去下载其最新版试用。<strong>该软件为商业软件</strong>。
<ul>
<li>如果你偶然路过，尝新而已，那只需<a href="http://www.powergrep.com/download.html" target="_blank">下载试用版</a>即可；</li>
<li>如果你觉得好用、准备常用、手有余钱、非正版不用，不妨<a http:="" www.powergrep.com="" buynow.html="">花美金购买</a>；要花人民币1000多块哟^_^</li>
<li><del datetime="2009-01-08T01:51:13+00:00">如果你喜欢它，同时你认为优秀的网络资源是应该和朋友免费分享的，从而想获得该软件的全功能免费版，好吧，我也成全你，请在本文后留言（附邮箱），我会把这个小东西的链接发给你(最新版为3.4.2，我手头的全功能版为3.3.3，也足够用了)。</del><strong>更新：</strong><br />
请移步至此下载<a href="http://iregex.org/blog/powergrep350.html">PowerGREP 3.5.0</a>版。</li>
</ul>
<p>&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;</p>
]]></content:encoded>
			<wfw:commentRss>http://iregex.org/blog/powergrep.html/feed</wfw:commentRss>
		<slash:comments>114</slash:comments>
		</item>
	</channel>
</rss>
