<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss 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/" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0">

<channel>
	<title>没有比人更高的山</title>
	
	<link>http://www.zhlwish.com</link>
	<description>Where there is a will there is a way.</description>
	<lastBuildDate>Thu, 03 May 2012 07:43:45 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/zhlwish/etKj" /><feedburner:info uri="zhlwish/etkj" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><item>
		<title>用MySQL Procedure同时像级联表插入数据</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/X5Zd_f3GLKc/</link>
		<comments>http://www.zhlwish.com/2012/04/17/mysql-procedure/#comments</comments>
		<pubDate>Tue, 17 Apr 2012 15:46:43 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>
		<category><![CDATA[MySQL]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=1021</guid>
		<description><![CDATA[一个月以来都没写博客，这篇博客的目的是提醒自己继续写下去，顺便记下笔记，看官若无兴趣请直接飘过。 级联表是关系数据库存储领域模型（Domain Model）中一对多关系的不二法门，比如“学生”和“班级”，实在是常用得很。创建表时建立外键关联，查询时使用inner join或者多表联合查询非常便捷。不过插入数据则相对麻烦，因为关键关联的缘故，需要先插入主表，然后再插入从表，如果使用auto_increment主键，在插入从表之前必须获取刚刚插入主表时生成的ID。 举例来说，下面classes和students表通过外键class_id建立一对多关联： DROP TABLE IF EXISTS students; DROP TABLE IF EXISTS classes; DROP VIEW IF EXISTS student_in_class; &#160; CREATE TABLE classes&#40; id serial, name CHAR&#40;55&#41; NOT NULL, UNIQUE KEY cls_name &#40;name&#41;, PRIMARY KEY&#40;id&#41; &#41;; &#160; CREATE TABLE &#8230; <a href="http://www.zhlwish.com/2012/04/17/mysql-procedure/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/o1b3u6l6f0J9QUZYgSHCpcrHsvs/0/da"><img src="http://feedads.g.doubleclick.net/~a/o1b3u6l6f0J9QUZYgSHCpcrHsvs/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/o1b3u6l6f0J9QUZYgSHCpcrHsvs/1/da"><img src="http://feedads.g.doubleclick.net/~a/o1b3u6l6f0J9QUZYgSHCpcrHsvs/1/di" border="0" ismap="true"></img></a></p><blockquote><p>一个月以来都没写博客，这篇博客的目的是提醒自己继续写下去，顺便记下笔记，看官若无兴趣请直接飘过。</p></blockquote>
<p>级联表是关系数据库存储领域模型（Domain Model）中一对多关系的不二法门，比如“学生”和“班级”，实在是常用得很。创建表时建立外键关联，查询时使用inner join或者多表联合查询非常便捷。不过插入数据则相对麻烦，因为关键关联的缘故，需要先插入主表，然后再插入从表，如果使用auto_increment主键，在插入从表之前必须获取刚刚插入主表时生成的ID。</p>
<p><span id="more-1021"></span></p>
<p>举例来说，下面classes和students表通过外键class_id建立一对多关联：</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:Verdana,Courier New;"><span style="color: #993333; font-weight: bold;">DROP</span> <span style="color: #993333; font-weight: bold;">TABLE</span> <span style="color: #993333; font-weight: bold;">IF</span> <span style="color: #993333; font-weight: bold;">EXISTS</span> students;
<span style="color: #993333; font-weight: bold;">DROP</span> <span style="color: #993333; font-weight: bold;">TABLE</span> <span style="color: #993333; font-weight: bold;">IF</span> <span style="color: #993333; font-weight: bold;">EXISTS</span> classes;
<span style="color: #993333; font-weight: bold;">DROP</span> <span style="color: #993333; font-weight: bold;">VIEW</span> <span style="color: #993333; font-weight: bold;">IF</span> <span style="color: #993333; font-weight: bold;">EXISTS</span> student_in_class;
&nbsp;
<span style="color: #993333; font-weight: bold;">CREATE</span> <span style="color: #993333; font-weight: bold;">TABLE</span> classes<span style="color: #66cc66;">&#40;</span>
  id serial<span style="color: #66cc66;">,</span>
  name <span style="color: #993333; font-weight: bold;">CHAR</span><span style="color: #66cc66;">&#40;</span><span style="color: #cc66cc;">55</span><span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">NOT</span> <span style="color: #993333; font-weight: bold;">NULL</span><span style="color: #66cc66;">,</span>
  <span style="color: #993333; font-weight: bold;">UNIQUE</span> <span style="color: #993333; font-weight: bold;">KEY</span> cls_name <span style="color: #66cc66;">&#40;</span>name<span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">,</span>
  <span style="color: #993333; font-weight: bold;">PRIMARY</span> <span style="color: #993333; font-weight: bold;">KEY</span><span style="color: #66cc66;">&#40;</span>id<span style="color: #66cc66;">&#41;</span>
<span style="color: #66cc66;">&#41;</span>;
&nbsp;
<span style="color: #993333; font-weight: bold;">CREATE</span> <span style="color: #993333; font-weight: bold;">TABLE</span> students<span style="color: #66cc66;">&#40;</span>
  <span style="color: #993333; font-weight: bold;">NUMBER</span> <span style="color: #993333; font-weight: bold;">CHAR</span><span style="color: #66cc66;">&#40;</span><span style="color: #cc66cc;">11</span><span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">NOT</span> <span style="color: #993333; font-weight: bold;">NULL</span><span style="color: #66cc66;">,</span>
  name <span style="color: #993333; font-weight: bold;">VARCHAR</span><span style="color: #66cc66;">&#40;</span><span style="color: #cc66cc;">55</span><span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">NOT</span> <span style="color: #993333; font-weight: bold;">NULL</span><span style="color: #66cc66;">,</span>
  class_id <span style="color: #993333; font-weight: bold;">BIGINT</span> <span style="color: #993333; font-weight: bold;">UNSIGNED</span> <span style="color: #993333; font-weight: bold;">NOT</span> <span style="color: #993333; font-weight: bold;">NULL</span><span style="color: #66cc66;">,</span>
  <span style="color: #993333; font-weight: bold;">PRIMARY</span> <span style="color: #993333; font-weight: bold;">KEY</span><span style="color: #66cc66;">&#40;</span><span style="color: #993333; font-weight: bold;">NUMBER</span><span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">,</span>
  <span style="color: #993333; font-weight: bold;">FOREIGN</span> <span style="color: #993333; font-weight: bold;">KEY</span> <span style="color: #66cc66;">&#40;</span>class_id<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">REFERENCES</span> classes<span style="color: #66cc66;">&#40;</span>id<span style="color: #66cc66;">&#41;</span>
<span style="color: #66cc66;">&#41;</span>;</pre></div></div>

<p>为了查询数据方便，创建一个视图，只是简单的执行级联查询：</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:Verdana,Courier New;"><span style="color: #993333; font-weight: bold;">CREATE</span> <span style="color: #993333; font-weight: bold;">VIEW</span> student_in_class <span style="color: #993333; font-weight: bold;">AS</span>
<span style="color: #993333; font-weight: bold;">SELECT</span> <span style="color: #993333; font-weight: bold;">NUMBER</span><span style="color: #66cc66;">,</span> students<span style="color: #66cc66;">.</span>name stu_name<span style="color: #66cc66;">,</span> classes<span style="color: #66cc66;">.</span>name cls_name 
<span style="color: #993333; font-weight: bold;">FROM</span> students
<span style="color: #993333; font-weight: bold;">INNER</span> <span style="color: #993333; font-weight: bold;">JOIN</span> classes
<span style="color: #993333; font-weight: bold;">ON</span> classes<span style="color: #66cc66;">.</span>id<span style="color: #66cc66;">=</span>students<span style="color: #66cc66;">.</span>class_id;</pre></div></div>

<p>对于之前提出的两个表同时插入数据的问题，熟悉MySQL的朋友都知道，用下面的方法就行了，先插入主表classes，然后通过last_insert_id()获取刚刚插入的id，最后向从表students插入数据。</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:Verdana,Courier New;"><span style="color: #993333; font-weight: bold;">START</span> <span style="color: #993333; font-weight: bold;">TRANSACTION</span>;
<span style="color: #993333; font-weight: bold;">INSERT</span> <span style="color: #993333; font-weight: bold;">INTO</span> classes<span style="color: #66cc66;">&#40;</span>name<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">VALUE</span><span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">'Class 1'</span><span style="color: #66cc66;">&#41;</span>;
<span style="color: #993333; font-weight: bold;">INSERT</span> <span style="color: #993333; font-weight: bold;">INTO</span> students<span style="color: #66cc66;">&#40;</span><span style="color: #993333; font-weight: bold;">NUMBER</span><span style="color: #66cc66;">,</span> name<span style="color: #66cc66;">,</span> class_id<span style="color: #66cc66;">&#41;</span> 
  <span style="color: #993333; font-weight: bold;">VALUES</span><span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">'001'</span><span style="color: #66cc66;">,</span> <span style="color: #ff0000;">'Jim'</span><span style="color: #66cc66;">,</span> last_insert_id<span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">&#41;</span>;
commit;</pre></div></div>

<p>不过这样还是有个问题，如果待插入的数据和主表中已有的数据有重复怎么办呢？因此笔者对以上语句进行简单的封装，使用MySQL存储过程实现整个过程，首先对主表进行查询，如果不存在待插入的数据再插入：</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:Verdana,Courier New;"><span style="color: #993333; font-weight: bold;">DROP</span> <span style="color: #993333; font-weight: bold;">PROCEDURE</span> <span style="color: #993333; font-weight: bold;">IF</span> <span style="color: #993333; font-weight: bold;">EXISTS</span> insert_stu;
<span style="color: #993333; font-weight: bold;">CREATE</span> <span style="color: #993333; font-weight: bold;">PROCEDURE</span> insert_stu<span style="color: #66cc66;">&#40;</span>
  cls_name <span style="color: #993333; font-weight: bold;">CHAR</span><span style="color: #66cc66;">&#40;</span><span style="color: #cc66cc;">55</span><span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">,</span> 
  stu_num <span style="color: #993333; font-weight: bold;">CHAR</span><span style="color: #66cc66;">&#40;</span><span style="color: #cc66cc;">11</span><span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">,</span> 
  stu_name <span style="color: #993333; font-weight: bold;">VARCHAR</span><span style="color: #66cc66;">&#40;</span><span style="color: #cc66cc;">55</span><span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">&#41;</span>
<span style="color: #993333; font-weight: bold;">BEGIN</span> 
  <span style="color: #993333; font-weight: bold;">DECLARE</span> cls_id <span style="color: #993333; font-weight: bold;">BIGINT</span> <span style="color: #993333; font-weight: bold;">UNSIGNED</span>;
  <span style="color: #993333; font-weight: bold;">DECLARE</span> cls_cnt <span style="color: #993333; font-weight: bold;">INT</span>;
  <span style="color: #993333; font-weight: bold;">SELECT</span> <span style="color: #993333; font-weight: bold;">COUNT</span><span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">*</span><span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">INTO</span> cls_cnt <span style="color: #993333; font-weight: bold;">FROM</span> classes <span style="color: #993333; font-weight: bold;">WHERE</span> name<span style="color: #66cc66;">=</span>cls_name;
  <span style="color: #993333; font-weight: bold;">IF</span> cls_cnt <span style="color: #66cc66;">=</span> <span style="color: #cc66cc;">0</span> <span style="color: #993333; font-weight: bold;">THEN</span>
    <span style="color: #993333; font-weight: bold;">INSERT</span> <span style="color: #993333; font-weight: bold;">INTO</span> classes<span style="color: #66cc66;">&#40;</span>name<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">VALUE</span><span style="color: #66cc66;">&#40;</span>cls_name<span style="color: #66cc66;">&#41;</span>;
    <span style="color: #993333; font-weight: bold;">SET</span> cls_id <span style="color: #66cc66;">=</span> last_insert_id<span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">&#41;</span>;
  <span style="color: #993333; font-weight: bold;">ELSE</span>
    <span style="color: #993333; font-weight: bold;">SELECT</span> id <span style="color: #993333; font-weight: bold;">INTO</span> cls_id <span style="color: #993333; font-weight: bold;">FROM</span> classes <span style="color: #993333; font-weight: bold;">WHERE</span> name<span style="color: #66cc66;">=</span>cls_name;
  <span style="color: #993333; font-weight: bold;">END</span> <span style="color: #993333; font-weight: bold;">IF</span>;
&nbsp;
  <span style="color: #993333; font-weight: bold;">INSERT</span> <span style="color: #993333; font-weight: bold;">INTO</span> students<span style="color: #66cc66;">&#40;</span><span style="color: #993333; font-weight: bold;">NUMBER</span><span style="color: #66cc66;">,</span> name<span style="color: #66cc66;">,</span> class_id<span style="color: #66cc66;">&#41;</span> 
    <span style="color: #993333; font-weight: bold;">VALUES</span><span style="color: #66cc66;">&#40;</span>stu_num<span style="color: #66cc66;">,</span> stu_name<span style="color: #66cc66;">,</span> cls_id<span style="color: #66cc66;">&#41;</span>;
<span style="color: #993333; font-weight: bold;">END</span>;</pre></div></div>

<p>调用和检验该存储过程的方法如下：</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:Verdana,Courier New;"><span style="color: #993333; font-weight: bold;">CALL</span> insert_stu<span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">'Class 1'</span><span style="color: #66cc66;">,</span> <span style="color: #ff0000;">'001'</span><span style="color: #66cc66;">,</span> <span style="color: #ff0000;">'Bob'</span><span style="color: #66cc66;">&#41;</span>;
<span style="color: #993333; font-weight: bold;">CALL</span> insert_stu<span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">'Class 2'</span><span style="color: #66cc66;">,</span> <span style="color: #ff0000;">'002'</span><span style="color: #66cc66;">,</span> <span style="color: #ff0000;">'Jim'</span><span style="color: #66cc66;">&#41;</span>;
<span style="color: #993333; font-weight: bold;">CALL</span> insert_stu<span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">'Class 1'</span><span style="color: #66cc66;">,</span> <span style="color: #ff0000;">'003'</span><span style="color: #66cc66;">,</span> <span style="color: #ff0000;">'Li Lei'</span><span style="color: #66cc66;">&#41;</span>;
&nbsp;
<span style="color: #993333; font-weight: bold;">SELECT</span> <span style="color: #66cc66;">*</span> <span style="color: #993333; font-weight: bold;">FROM</span> student_in_class;</pre></div></div>

<p>最后一句是使用之前创建的视图查看输出结果：</p>
<pre>
number  stu_name  cls_name
001        Bob          Class 1
002        Jim           Class 2
003        Li Lei        Class 1
</pre>
<p><strong>参考：</strong></p>
<ol>
<li><a href="http://stackoverflow.com/questions/175066/sql-server-is-it-possible-to-insert-into-two-tables-at-the-same-time">Stackoverflow: Is it possible to insert into two tables at the same time?</a></li>
<li><a href="http://dev.mysql.com/doc/refman/5.0/en/create-procedure.html">http://dev.mysql.com/doc/refman/5.0/en/create-procedure.html</a></li>
<li><a href="http://dev.mysql.com/doc/refman/5.5/en/commit.html">MySQL transaction commit</a></li>
<li><a href="http://dev.mysql.com/doc/refman/5.0/en/information-functions.html#function_last-insert-id">MySQL last_insert_id() function</a></li>
<li><a href="http://dev.mysql.com/doc/refman/5.5/en/if-statement.html">MySQL If statement</a></li>
</ol>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/X5Zd_f3GLKc" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2012/04/17/mysql-procedure/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2012/04/17/mysql-procedure/</feedburner:origLink></item>
		<item>
		<title>Linux上diff命令详解</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/XAL2Q2nP4LE/</link>
		<comments>http://www.zhlwish.com/2012/03/05/linux-dif/#comments</comments>
		<pubDate>Mon, 05 Mar 2012 15:13:32 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>
		<category><![CDATA[shell]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=972</guid>
		<description><![CDATA[diff程序是linux上非常重要的工具，用于比较文件的内容，特别是比较两个版本不同的文件(本文中的a.c、b.c可以理解为两个版本的同一个文件，b.c是在a.c的基础上的修正版)以找到改动的地方。diff在命令行中打印每一个行的改动。最新版本的diff还支持二进制文件。diff程序的输出被称为补丁(patch)，因为unix系统中还有一个patch程序，可以根据diff的输出将a.c的文件内容更新为b.c。diff是svn、cvs、git等版本控制工具不可或缺的一部分。 diff和patch实例 下面用一个实例来讲述diff和patch的使用。 文件a.c的内容如下： #include &#60;stdio.h&#62; &#160; int main&#40;int argc, char *argv&#91;&#93;&#41; &#123; // add code here return 0; &#125; 文件b.c的内容如下: #include &#60;stdio.h&#62; &#160; int main&#40;int argc, char *argv&#91;&#93;&#41; &#123; printf&#40;&#34;Hello world&#34;&#41;; return 0; &#125; 执行命令： diff a.c b.c &#62; &#8230; <a href="http://www.zhlwish.com/2012/03/05/linux-dif/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/apXGMWMlPhnRyPnCnvj_OOgTMo4/0/da"><img src="http://feedads.g.doubleclick.net/~a/apXGMWMlPhnRyPnCnvj_OOgTMo4/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/apXGMWMlPhnRyPnCnvj_OOgTMo4/1/da"><img src="http://feedads.g.doubleclick.net/~a/apXGMWMlPhnRyPnCnvj_OOgTMo4/1/di" border="0" ismap="true"></img></a></p><p><a href="http://en.wikipedia.org/wiki/Diff" target="_blank">diff</a>程序是linux上非常重要的工具，用于比较文件的内容，特别是比较两个版本不同的文件(本文中的a.c、b.c可以理解为两个版本的同一个文件，b.c是在a.c的基础上的修正版)以找到改动的地方。diff在命令行中打印每一个行的改动。最新版本的diff还支持二进制文件。diff程序的输出被称为补丁(patch)，因为unix系统中还有一个<a href="http://en.wikipedia.org/wiki/Patch_(Unix)" target="_blank">patch</a>程序，可以根据diff的输出将a.c的文件内容更新为b.c。diff是svn、cvs、git等版本控制工具不可或缺的一部分。<br />
<span id="more-972"></span></p>
<h2>diff和patch实例</h2>
<p>下面用一个实例来讲述diff和patch的使用。<br />
文件a.c的内容如下：</p>

<div class="wp_syntax"><div class="code"><pre class="c" style="font-family:Verdana,Courier New;"><span style="color: #339933;">#include &lt;stdio.h&gt;</span>
&nbsp;
<span style="color: #993333;">int</span> main<span style="color: #009900;">&#40;</span><span style="color: #993333;">int</span> argc<span style="color: #339933;">,</span> <span style="color: #993333;">char</span> <span style="color: #339933;">*</span>argv<span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #666666; font-style: italic;">// add code here</span>
    <span style="color: #b1b100;">return</span> <span style="color: #0000dd;">0</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>文件b.c的内容如下:</p>

<div class="wp_syntax"><div class="code"><pre class="c" style="font-family:Verdana,Courier New;"><span style="color: #339933;">#include &lt;stdio.h&gt;</span>
&nbsp;
<span style="color: #993333;">int</span> main<span style="color: #009900;">&#40;</span><span style="color: #993333;">int</span> argc<span style="color: #339933;">,</span> <span style="color: #993333;">char</span> <span style="color: #339933;">*</span>argv<span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #000066;">printf</span><span style="color: #009900;">&#40;</span><span style="color: #ff0000;">&quot;Hello world&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #b1b100;">return</span> <span style="color: #0000dd;">0</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>执行命令：</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:Verdana,Courier New;"><span style="color: #c20cb9; font-weight: bold;">diff</span> a.c b.c <span style="color: #000000; font-weight: bold;">&gt;</span> b.patch</pre></div></div>

<p>输出b.patch的内容如下：</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:Verdana,Courier New;">5c5
&lt;     // add code here 
--- 
&gt;     printf(&quot;Hello world&quot;);</pre></div></div>

<p>接着执行下面的命令就可以将patch文件b.patch应用于a.c文件上，将a.c文件的内容更新为新的版本(即b.c)</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:Verdana,Courier New;"><span style="color: #c20cb9; font-weight: bold;">patch</span> a.c b.patch</pre></div></div>

<p>a.c的内容被更新为b.c的内容：</p>

<div class="wp_syntax"><div class="code"><pre class="c" style="font-family:Verdana,Courier New;"><span style="color: #339933;">#include &lt;stdio.h&gt;</span>
&nbsp;
<span style="color: #993333;">int</span> main<span style="color: #009900;">&#40;</span><span style="color: #993333;">int</span> argc<span style="color: #339933;">,</span> <span style="color: #993333;">char</span> <span style="color: #339933;">*</span>argv<span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #000066;">printf</span><span style="color: #009900;">&#40;</span><span style="color: #ff0000;">&quot;Hello world&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #b1b100;">return</span> <span style="color: #0000dd;">0</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>不过，diff的输出让人读起来很废劲，因为这个输出本来就不是给人看的，如果你知道一点关于<a href="http://en.wikipedia.org/wiki/Ed_(Unix)" target="_blank">ed</a>编辑器的用法，就容易理解了。最开始的时候diff的输出不是这种格式的，后来受到<a href="http://en.wikipedia.org/wiki/Ed_(Unix)" target="_blank">ed</a>编辑器的影响才变成这个样子，至于其发展历程请移步<a href="http://en.wikipedia.org/wiki/Diff#History" target="_blank">维基百科</a>，因此在解释diff的输出之前，先简单介绍一下<a href="http://en.wikipedia.org/wiki/Ed_(Unix)" target="_blank">ed</a>编辑器。</p>
<h2>ed编辑器</h2>
<p>ed是一个交互式的文本编辑器，类Unix系统中有很多很神奇的编辑器，号称神器的有vi、vim、emacs，还有常规意义的编辑器nano、gedit，还有看起来很诡异的sed(<strong>S</strong>tream <strong>Ed</strong>itor)、awk，ed这是另一个很诡异的编辑器，不同于前面的任何一种。</p>
<p>打开shell，按次序输入如下的命令(需要一句一句的敲)：</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:Verdana,Courier New;">touch c.c
ed c.c
0a
#include &lt;stdio.h&gt;
int main(int argc, char *argv[])
{
    // add code here
    return 0;
}
.
w
q</pre></div></div>

<p>使用cat命令查看c.c，该文件的内容就是上面代码中“0a”和“.”之前代码。</p>
<p>和vim一样，ed通过一系列的命令来编辑文件：</p>
<ul>
<li>“ed c.c”表示用ed对文件c.c进行编辑</li>
<li>“0a”表示在第0行后进行添加(a表示add，同样，d表示删除，c表示修改)</li>
<li>接着输入需要添加的内容，输入完成后换一行，输入“.&lt;CR&gt;”(&lt;CR&gt;表示回车)，表示输入完成</li>
<li>输入“w&lt;CR&gt;”表示保存文件</li>
<li>输入“q&lt;CR&gt;”表示退出编辑器</li>
</ul>
<p>ed编辑器的好处在于可以将一系列命令写成一个文件，然后进行批量执行。比如需要在所有的源代码开头加上版权信息，则可以编写如下的ed文件，保存为add_header:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:Verdana,Courier New;">0a
/**
 * &amp;copy; 2012 zhlwish.com
 */
.
w
q</pre></div></div>

<p>然后写一段shell脚本对源代码文件进行遍历，对每个代码执行如下代码即可批量对源代码文件添加版权信息：</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:Verdana,Courier New;"><span style="color: #c20cb9; font-weight: bold;">ed</span> a.c <span style="color: #000000; font-weight: bold;">&lt;</span> add_header</pre></div></div>

<p>关于ed的命令和其他方法请参考<a href="http://www.softpanorama.org/Editors/Exorama/index.shtml" target="_blank">Unix ed Editor Command Set</a>本文不详述。</p>
<h2>diff的输出</h2>
<p>diff的输出格式是对ed脚本(ed script)的一种扩展，遵循ed的命令语法，添加了”&lt;”和”&gt;”分别用于表示新文件的内容和旧文件的内容，比如前文中diff的输出可以按如下方式理解：</p>
<ul>
<li>“5c5”表示a.c的第5行有改动(<strong>c</strong>hange)，改动后为b.c的第5行</li>
<li>“&lt;     // add code here”表示a.c的第5行的内容</li>
<li>“&#8212; ”是分隔符</li>
<li>“&gt;     printf(“Hello world”);”表示b.c文件的第5行的内容</li>
</ul>
<p>当然还有更复杂的情况，如“3c3,6”、“6d8”，前者表示旧版本文件中的第3行被修改，对应新文件中的第3-6行，后者表示旧版本文件的第6行被删除，在新文件中是第8行。</p>
<p>可以通过参数指定diff输出格式，有兴趣的笔者可以分别进行尝试：</p>
<ul>
<li>-e &#8211;ed 输出为ed命令格式</li>
<li>-n &#8211;rcs 输出为rcs命令格式</li>
<li>-y 输出为两列对照模式</li>
<li>-c 输出为上下文模式</li>
</ul>
<h2>diff的选项</h2>
<p>除以上选项外，diff的有用的选项还包括：</p>
<ul>
<li>-r：当diff的参数为文件夹时，diff会遍历整个文件夹对新旧文件夹下同名的文件进行比较</li>
<li>-w：忽略所有空格和制表符，将所有其他空白字符串视为一致。例如，if ( a == b ) 与 if(a==b) 相等。</li>
<li>-i：忽略字母大小写。例如，小写 a 被认为同大写 A 一样。</li>
</ul>
<p>因为成文仓促，不免有不对之处，敬请读者指正。(全文完)</p>
<h2>参考资料</h2>
<ul>
<li><a href="http://baike.baidu.com/view/1374858.htm" target="_blank">Linux命令diff</a></li>
<li><a href="http://www.tsnc.edu.cn/tsnc_wgrj/doc/sed.htm" target="_blank">Sed学习笔记</a></li>
<li><a href="http://wiki.bash-hackers.org/howto/edit-ed" target="_blank">Editing files with the ed text editor from scripts</a></li>
<li><a href="http://www.softpanorama.org/Editors/Exorama/index.shtml" target="_blank">Unix ed Editor Command Set</a></li>
<li><a href="http://www.youtube.com/watch?gl=JP&#038;v=jxlcIMPyAt4" target="_blank">Hello World” with ed editor</a>(Youtube)</li>
<li><a href="http://www.ibm.com/developerworks/cn/linux/l-diffp/" target="_blank">用Diff和Patch工具维护源码</a></li>
</ul>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/XAL2Q2nP4LE" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2012/03/05/linux-dif/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2012/03/05/linux-dif/</feedburner:origLink></item>
		<item>
		<title>[转载]陈丹青：民国是历史还是现实</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/qCjN7Gb4Q3M/</link>
		<comments>http://www.zhlwish.com/2012/02/22/chendanqing-minguo/#comments</comments>
		<pubDate>Wed, 22 Feb 2012 12:57:21 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>
		<category><![CDATA[民国]]></category>
		<category><![CDATA[陈丹青]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=965</guid>
		<description><![CDATA[该视频来自于2011年9月12日举办的理想国文化沙龙，文字稿来源于优米网，本人有部分修正。 视频 文字稿 今天这个现场满有意思的，也许同学们都知道隔壁就是东交民巷，八国联军来的时候早期的国民党往那逃。马路对过是北京火车站，张作霖进入北京就是在那下车，李鸿章进入北京，然后，1949年毛泽东带着文武官员到火车站迎接宋庆龄从上海到北京，就在马路对过，现在那个火车站废弃不用了，但建筑还在。再往西一点就是大前门，我看过一张蛮珍贵的照片，1948年北平已经被包围了，不知道从什么角度拍过去，当时天安门广场是荒草场，但是大前门挂了一张蒋中正的巨大的照片，据说解放军进城以后弄开国大典，先前的选择不是在天安门广场而是大前门，因为整个军队入城的仪式是由南向北，经过现在的天桥往北走，后来不知道怎样改成天安门，所以我们小时候有一首歌叫“我爱北京天安门”，如果当时选了大前门就是“我爱北京大前门”。这个地方据我知道是民国时期美国驻中国领事馆，司徒雷登就在那上班吗？毛泽东有一篇很重要的文章“别了，司徒雷登”，意思是咱们到此为止，所以司徒雷登当时就在我们上面。不过我今天进来的时候军警林立，我才意识到这是靠天安门的地方。 我觉得“民国是历史的还是现实”是一个好话题，但是如果记者问我，我会答不上来，因为现实和历史这两个词不能定义，可能指过去已经不在场或者不奏效的就叫历史。而现实还在，还有作用，还在发生，可能就是现实。讲下去就会有点错位。我记得1966年文革爆发，毛泽东狠狠的对全党和全国人民说，无产阶级文化大革命是革命派和反革命、共产党和国民党的继续斗争。那一年我13岁，戴着红领巾，而且共和国也已经17岁了，我听了毛泽东这么一番话心惊肉跳，我想怎么民国还没有过去，国民党还在？这是我小时候的印象。现在我明白毛泽东其实没有错，他那一年70多岁，除了逃到台湾的那部分国民党，他的许多民国朋友和敌人都还活着，曾经顶撞过他的梁漱溟，曾经杀过共产党的李济深都住在北京，一大群民主人士、第三势力，还有他的同志们。而毛泽东本人，包括周恩来、朱德等共产党领导人曾经就是国民党员，在国民政府做官，当着蒋介石的面喊“蒋委员长万岁”。所以毛泽东想起民国和我当时13岁的小孩听见的民国感觉是不一样的，他一想起就是一大群使他不安的活人。 1976文革结束至今35年，远远超过毛泽东回想民国的时间距离，我们或者可以问文革是历史还是现实。30多年来我们的文人和出版社都在做历史研究，出历史书，在座诸位也想必喜欢读历史。读历史为了什么？克罗齐说的还没过时，所有的历史都是当代史。今年算是借辛亥百年，我们有理由在市面上公开说民国，为了尊敬今年另一个大的纪念，我特地到钻到电影院看了《建党伟业》，看完以后手机来了几条短信，其中有一条非常聪明，把建党和民国一块纪念了，大家可能读过这个短信，我再念一遍：《建党伟业》是一部向北洋军阀政府致敬的电影，该片用生动的镜头、精彩的案例、温馨的细节为我们描述这样一个时代：报纸可以私人控股，新闻可以批评政府，大学可以学术独立，学生可以上街游行，群众可以秘密结社，警察不可随便抓人，权力有边界，法律有作用，人权有保障，穷人有活路，青年有理想。我不知道这个手机短信作者是谁，大家为他鼓掌。总之这部电影拍着不小心把民国史拍出来，我猜韩三平没有想到这效果。虽然这条短信谈到历史又明明指向现实，简直已经回答了论坛的话题，但是我不能念一条短信交差，所以赶紧清理我可怜的历史知识，看看民国哪些往事已经过去了，算是历史，哪些往事还在，算是现实。 先说成为历史的那个民国。首先民国的战乱过去了，我们几代人何等幸福，60年来没有遭遇任何外敌侵略。文革的武斗当然是毛泽东所说的继续斗争，但是死伤者者没有一个是国民党员，而是和在座一样年轻的男女。昨天听秦晖先生说起广西的武斗，他看到高射炮平射和在越南用的炸药弹。当时他十几岁，武斗过后清理现场，巨大的瓦砾堆，只要闻到臭味就可以掘起一具尸体，但这个跟民国战争不能比。 其次半殖民地时代过去了，帝国主义在中国的殖民区域完全消失，虽然现在上海、武汉、南京、天津等市政府竭力刷新英租界、法租界所有好地段为旅游业赚大钱，但是像康有为、梁启超、胡适、鲁迅这样的闯祸胚子再想闹事没有地方躲了，即便赖昌星逃到加拿大还是回来戴手铐。 再其次，中国分裂的时代过去了，民国时期或者先后或者同期，有过南京政府、武汉政府、瑞金苏维埃政府，有过延安政府，有过重庆政府，还有过满洲国。东北的满洲国有东三省的铁路网，忽然归张作霖管，忽然归日本人管，忽然归苏联人管。今天全国的铁路畅通无阻，新建的铁路线和载客量是民国时期的几十、上百倍，虽然最近发生动车追尾暴死几十个人，但成绩绝对是主要的。你们不相信吗？反正我是相信。 再再其次，国家的弱势完全过去了，民国政府根本没有象样的空军和海军，要靠美国人和苏联人帮忙，后来匆忙培养自己的空军飞行员，在对日保卫国家的空战中几乎全部死光。我们的空军非常棒，都活着，还驾驶飞船进入太空，当然我们自己的航空母舰马上要问世了。 此外，民国的多党政治彻底过去了，但这个是敏感的问题，我不敢说。我敢说的是民国教育的黄金时代完全过去了。蔡元培的北大、梅贻琦的清华、张伯苓的南开、竺可桢的浙大绝对成为历史，一去不复返。现在他们想当校长，先得通过层层审查，接着慢慢混到正局级或者副部级才能填写申请表听后审查。另外蔡元培为陈独秀假造学历，梁启超延聘没有学位的陈寅恪再也不能得逞了。 民国出版的自由和言论自由也过去了，像张元济、王云五这样的出版大亨再也不必辛辛苦苦自己开办商务印书馆之类，邵飘萍、史量才这样的亡命记者和报业大王再也不会被枪毙被暗杀。当今中国的出版商、记者、撰稿人一律享受新闻出版总署的保护，非常安全、非常正确、非常和谐，所有人都很乖，很懂事，绝对不怕被枪毙。 最后一个可能被忽略的巨大事项也成为历史，那就是古文教育，文言文和白话文并存，繁体字等等构成的汉语语言生态成为历史了。在民国所有识字的人既懂文言也懂白话，既用繁体字也用当时通行的简体字，随着民国的消亡，汉语的生态永远消亡了，我们当世只有白话文，只有简体字。 民国许多其他事都成为历史，永远过去，一部分是历史进程本身，比如现代化。一部分是政治原因，比如无所不在的禁止。但限于发言时间不能一一例举，现在我来快速例举民国仍在今天奏效的部分现实。比如，据说民国的灭亡原因主要是贪污腐化裙带关系，今天所有被指控的民国腐败者远远无法和共和国贪官比。从资料披露，一向被认为巨贪的宋子文不但没有怎么贪污，而且是强硬的民族主义者。就算他财富不很清楚，但和今天随便哪个被揭露的地方贪官相比，简直羞煞人。当年为蒋介石负责运送黄金到台湾的一位老先生，我忘了他的名字，我在三联周刊看过他的报道，没有贪污过一分钱，死了以后他的存折拿出来只有8万美金。至于裙带关系不用我来说，今日权利格局的血缘背景，一点不比民国时期更薄，如果需要证据，我希望学者做统计。民国社会层面世俗生活的状况一度被铲除，之后20多年大规模卷土重来，比如色情业，比如赌博、走私、黑社会，都在渐渐与民国接轨。 此外改革开放30年，凡私人生活逐渐被允许拓展的空间，都是民国生活形态的死灰复燃。比如选美、时尚、娱乐、交际、享受、奢侈等等，这些都是好消息，大家不要以为这是我们今天时代的稀罕事情，民国时期早就有了。这种活泼可喜的生活形态，有的远远比民国时期土，因为有教养的阶层消失了，有的远远比民国更洋，因为民国人还没机会领教西方二次现代化以后的种种新花样。 时间关系，以上关于历史与现实的类比十分粗糙，不准确、不可靠，希望专家批评指教。但是坦白说，我以为民国对于今天，对于大部分年轻人，既不是历史，也不是现实，为什么？ 因为60年来我们接受了空前成功的愚民教育，这种教育的核心就是不要让你知道过去，直到你对过去漠不关心。现在绝大部分中国人，尤其是年轻人，没有历史感，没有现实感，对共和国不了解，更不了解民国。30年前邓小平说国著名的话，体育要从娃娃抓起。其实真正要紧的是历史要从娃娃抓起。 最近听说秦晖请大学生自己做调查，题目叫你最熟悉的陌生人。请今天的80后、90后向父母或者祖父母追问民国的往事，这是了解民国最最有效、最最人性的方式，因为民国就在每个家庭。刚才马世芳说了他的家庭，我们大陆有很多这样的家庭，我的父母就是民国人，诸位祖父母也是民国人。据说问到一半，就有家长出来阻拦，不要再问了，也不愿再说。为什么？就是害怕历史提醒现实，因为今天的现实害怕历史，以致历史也害怕今天。因为民国的历史就是活人，所有民国的过来人迫于现实回避历史，不谈历史，这就是我们今天普遍的现实。所以最熟悉的陌生人是个好题目，你是爹妈生出来的，你不了解爹妈，中华人民共和国是民国生出来，可是共和国的老百姓不了解民国。长期不了解、不说就不会想了解，不想说；长期的不说几代人不说，等于没有这回事。比如80后，比如89年出生的孩子，别说1949年前的民国，连1989年北京发生什么事绝大部分不知道。我们的爹妈也未必知道，你们在北京的爹妈可能知道，但是他们不愿说。这样不说、不说，每个家庭都对孩子瞒着往事，整个国家对人民也瞒着往事，瞒得久了，30年、60年瞒下来，将来还会瞒下去。你现在到马路上抓一个小青年问他你要不要听民国，他掉头就走，根本没有兴趣。所以我觉得民国既不是历史，也不是现实。但是今天在座的年轻人比较不一样，大好秋天哪里不能去，你们要跑到这里来听民国，什么意思呢？但是你们还是来了。谢谢大家。]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/rwi9dOVz0ygj1bUuh09GYEf2FtY/0/da"><img src="http://feedads.g.doubleclick.net/~a/rwi9dOVz0ygj1bUuh09GYEf2FtY/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/rwi9dOVz0ygj1bUuh09GYEf2FtY/1/da"><img src="http://feedads.g.doubleclick.net/~a/rwi9dOVz0ygj1bUuh09GYEf2FtY/1/di" border="0" ismap="true"></img></a></p><p>该视频来自于2011年9月12日举办的<a href="http://special.umiwi.com/Utopia/" target="_blank">理想国文化沙龙</a>，文字稿来源于<a href="http://special.umiwi.com/2011/0911/36231_7.shtml" target="_blank">优米网</a>，本人有部分修正。</p>
<p style="text-align: center;"><strong>视频</strong></p>
<p style="text-align: center;"><object width="420" height="363"><param name="movie" value="http://www.tudou.com/v/0jDIu-Q0aoo"></param><param name="allowFullScreen" value="true"></param><param name="allowscriptaccess" value="never"></param><param name="allownetworking" value="internal"></param><param name="flashvars" value="" /><embed src="http://www.tudou.com/v/0jDIu-Q0aoo" type="application/x-shockwave-flash" allowscriptaccess="never" allownetworking="internal" allowfullscreen="true" width="420" height="363" flashvars=""></embed></object></p>
<p style="text-align: center;"><strong>文字稿</strong></p>
<p>今天这个现场满有意思的，也许同学们都知道隔壁就是东交民巷，八国联军来的时候早期的国民党往那逃。马路对过是北京火车站，张作霖进入北京就是在那下车，李鸿章进入北京，然后，1949年毛泽东带着文武官员到火车站迎接宋庆龄从上海到北京，就在马路对过，现在那个火车站废弃不用了，但建筑还在。再往西一点就是大前门，我看过一张蛮珍贵的照片，1948年北平已经被包围了，不知道从什么角度拍过去，当时天安门广场是荒草场，但是大前门挂了一张蒋中正的巨大的照片，据说解放军进城以后弄开国大典，先前的选择不是在天安门广场而是大前门，因为整个军队入城的仪式是由南向北，经过现在的天桥往北走，后来不知道怎样改成天安门，所以我们小时候有一首歌叫“我爱北京天安门”，如果当时选了大前门就是“我爱北京大前门”。这个地方据我知道是民国时期美国驻中国领事馆，司徒雷登就在那上班吗？毛泽东有一篇很重要的文章“别了，司徒雷登”，意思是咱们到此为止，所以司徒雷登当时就在我们上面。不过我今天进来的时候军警林立，我才意识到这是靠天安门的地方。<span id="more-965"></span></p>
<p>我觉得“民国是历史的还是现实”是一个好话题，但是如果记者问我，我会答不上来，因为现实和历史这两个词不能定义，可能指过去已经不在场或者不奏效的就叫历史。而现实还在，还有作用，还在发生，可能就是现实。讲下去就会有点错位。我记得1966年文革爆发，毛泽东狠狠的对全党和全国人民说，无产阶级文化大革命是革命派和反革命、共产党和国民党的继续斗争。那一年我13岁，戴着红领巾，而且共和国也已经17岁了，我听了毛泽东这么一番话心惊肉跳，我想怎么民国还没有过去，国民党还在？这是我小时候的印象。现在我明白毛泽东其实没有错，他那一年70多岁，除了逃到台湾的那部分国民党，他的许多民国朋友和敌人都还活着，曾经顶撞过他的梁漱溟，曾经杀过共产党的李济深都住在北京，一大群民主人士、第三势力，还有他的同志们。而毛泽东本人，包括周恩来、朱德等共产党领导人曾经就是国民党员，在国民政府做官，当着蒋介石的面喊“蒋委员长万岁”。所以毛泽东想起民国和我当时13岁的小孩听见的民国感觉是不一样的，他一想起就是一大群使他不安的活人。</p>
<p>1976文革结束至今35年，远远超过毛泽东回想民国的时间距离，我们或者可以问文革是历史还是现实。30多年来我们的文人和出版社都在做历史研究，出历史书，在座诸位也想必喜欢读历史。读历史为了什么？克罗齐说的还没过时，所有的历史都是当代史。今年算是借辛亥百年，我们有理由在市面上公开说民国，为了尊敬今年另一个大的纪念，我特地到钻到电影院看了《建党伟业》，看完以后手机来了几条短信，其中有一条非常聪明，把建党和民国一块纪念了，大家可能读过这个短信，我再念一遍：《建党伟业》是一部向北洋军阀政府致敬的电影，该片用生动的镜头、精彩的案例、温馨的细节为我们描述这样一个时代：报纸可以私人控股，新闻可以批评政府，大学可以学术独立，学生可以上街游行，群众可以秘密结社，警察不可随便抓人，权力有边界，法律有作用，人权有保障，穷人有活路，青年有理想。我不知道这个手机短信作者是谁，大家为他鼓掌。总之这部电影拍着不小心把民国史拍出来，我猜韩三平没有想到这效果。虽然这条短信谈到历史又明明指向现实，简直已经回答了论坛的话题，但是我不能念一条短信交差，所以赶紧清理我可怜的历史知识，看看民国哪些往事已经过去了，算是历史，哪些往事还在，算是现实。</p>
<p>先说成为历史的那个民国。首先民国的战乱过去了，我们几代人何等幸福，60年来没有遭遇任何外敌侵略。文革的武斗当然是毛泽东所说的继续斗争，但是死伤者者没有一个是国民党员，而是和在座一样年轻的男女。昨天听秦晖先生说起广西的武斗，他看到高射炮平射和在越南用的炸药弹。当时他十几岁，武斗过后清理现场，巨大的瓦砾堆，只要闻到臭味就可以掘起一具尸体，但这个跟民国战争不能比。</p>
<p>其次半殖民地时代过去了，帝国主义在中国的殖民区域完全消失，虽然现在上海、武汉、南京、天津等市政府竭力刷新英租界、法租界所有好地段为旅游业赚大钱，但是像康有为、梁启超、胡适、鲁迅这样的闯祸胚子再想闹事没有地方躲了，即便赖昌星逃到加拿大还是回来戴手铐。</p>
<p>再其次，中国分裂的时代过去了，民国时期或者先后或者同期，有过南京政府、武汉政府、瑞金苏维埃政府，有过延安政府，有过重庆政府，还有过满洲国。东北的满洲国有东三省的铁路网，忽然归张作霖管，忽然归日本人管，忽然归苏联人管。今天全国的铁路畅通无阻，新建的铁路线和载客量是民国时期的几十、上百倍，虽然最近发生动车追尾暴死几十个人，但成绩绝对是主要的。你们不相信吗？反正我是相信。</p>
<p>再再其次，国家的弱势完全过去了，民国政府根本没有象样的空军和海军，要靠美国人和苏联人帮忙，后来匆忙培养自己的空军飞行员，在对日保卫国家的空战中几乎全部死光。我们的空军非常棒，都活着，还驾驶飞船进入太空，当然我们自己的航空母舰马上要问世了。</p>
<p>此外，民国的多党政治彻底过去了，但这个是敏感的问题，我不敢说。我敢说的是民国教育的黄金时代完全过去了。蔡元培的北大、梅贻琦的清华、张伯苓的南开、竺可桢的浙大绝对成为历史，一去不复返。现在他们想当校长，先得通过层层审查，接着慢慢混到正局级或者副部级才能填写申请表听后审查。另外蔡元培为陈独秀假造学历，梁启超延聘没有学位的陈寅恪再也不能得逞了。</p>
<p>民国出版的自由和言论自由也过去了，像张元济、王云五这样的出版大亨再也不必辛辛苦苦自己开办商务印书馆之类，邵飘萍、史量才这样的亡命记者和报业大王再也不会被枪毙被暗杀。当今中国的出版商、记者、撰稿人一律享受新闻出版总署的保护，非常安全、非常正确、非常和谐，所有人都很乖，很懂事，绝对不怕被枪毙。</p>
<p>最后一个可能被忽略的巨大事项也成为历史，那就是古文教育，文言文和白话文并存，繁体字等等构成的汉语语言生态成为历史了。在民国所有识字的人既懂文言也懂白话，既用繁体字也用当时通行的简体字，随着民国的消亡，汉语的生态永远消亡了，我们当世只有白话文，只有简体字。</p>
<p>民国许多其他事都成为历史，永远过去，一部分是历史进程本身，比如现代化。一部分是政治原因，比如无所不在的禁止。但限于发言时间不能一一例举，现在我来快速例举民国仍在今天奏效的部分现实。比如，据说民国的灭亡原因主要是贪污腐化裙带关系，今天所有被指控的民国腐败者远远无法和共和国贪官比。从资料披露，一向被认为巨贪的宋子文不但没有怎么贪污，而且是强硬的民族主义者。就算他财富不很清楚，但和今天随便哪个被揭露的地方贪官相比，简直羞煞人。当年为蒋介石负责运送黄金到台湾的一位老先生，我忘了他的名字，我在三联周刊看过他的报道，没有贪污过一分钱，死了以后他的存折拿出来只有8万美金。至于裙带关系不用我来说，今日权利格局的血缘背景，一点不比民国时期更薄，如果需要证据，我希望学者做统计。民国社会层面世俗生活的状况一度被铲除，之后20多年大规模卷土重来，比如色情业，比如赌博、走私、黑社会，都在渐渐与民国接轨。</p>
<p>此外改革开放30年，凡私人生活逐渐被允许拓展的空间，都是民国生活形态的死灰复燃。比如选美、时尚、娱乐、交际、享受、奢侈等等，这些都是好消息，大家不要以为这是我们今天时代的稀罕事情，民国时期早就有了。这种活泼可喜的生活形态，有的远远比民国时期土，因为有教养的阶层消失了，有的远远比民国更洋，因为民国人还没机会领教西方二次现代化以后的种种新花样。</p>
<p>时间关系，以上关于历史与现实的类比十分粗糙，不准确、不可靠，希望专家批评指教。但是坦白说，我以为民国对于今天，对于大部分年轻人，既不是历史，也不是现实，为什么？</p>
<p>因为60年来我们接受了空前成功的愚民教育，这种教育的核心就是不要让你知道过去，直到你对过去漠不关心。现在绝大部分中国人，尤其是年轻人，没有历史感，没有现实感，对共和国不了解，更不了解民国。30年前邓小平说国著名的话，体育要从娃娃抓起。其实真正要紧的是历史要从娃娃抓起。</p>
<p>最近听说秦晖请大学生自己做调查，题目叫你最熟悉的陌生人。请今天的80后、90后向父母或者祖父母追问民国的往事，这是了解民国最最有效、最最人性的方式，因为民国就在每个家庭。刚才马世芳说了他的家庭，我们大陆有很多这样的家庭，我的父母就是民国人，诸位祖父母也是民国人。据说问到一半，就有家长出来阻拦，不要再问了，也不愿再说。为什么？就是害怕历史提醒现实，因为今天的现实害怕历史，以致历史也害怕今天。因为民国的历史就是活人，所有民国的过来人迫于现实回避历史，不谈历史，这就是我们今天普遍的现实。所以最熟悉的陌生人是个好题目，你是爹妈生出来的，你不了解爹妈，中华人民共和国是民国生出来，可是共和国的老百姓不了解民国。长期不了解、不说就不会想了解，不想说；长期的不说几代人不说，等于没有这回事。比如80后，比如89年出生的孩子，别说1949年前的民国，连1989年北京发生什么事绝大部分不知道。我们的爹妈也未必知道，你们在北京的爹妈可能知道，但是他们不愿说。这样不说、不说，每个家庭都对孩子瞒着往事，整个国家对人民也瞒着往事，瞒得久了，30年、60年瞒下来，将来还会瞒下去。你现在到马路上抓一个小青年问他你要不要听民国，他掉头就走，根本没有兴趣。所以我觉得民国既不是历史，也不是现实。但是今天在座的年轻人比较不一样，大好秋天哪里不能去，你们要跑到这里来听民国，什么意思呢？但是你们还是来了。谢谢大家。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/qCjN7Gb4Q3M" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2012/02/22/chendanqing-minguo/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2012/02/22/chendanqing-minguo/</feedburner:origLink></item>
		<item>
		<title>耶鲁大学、北京大学和华中科技大学的宣传片</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/UNltDdmPYNY/</link>
		<comments>http://www.zhlwish.com/2012/02/13/yale-pku-hust/#comments</comments>
		<pubDate>Mon, 13 Feb 2012 03:56:16 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=955</guid>
		<description><![CDATA[最近耶鲁大学和北京大学的宣传片对比在微博上很火，对北大也是骂声一片，毕竟人们对北大的期望要更高些。耶鲁大学的宣传片很运动、很活力、很激情，看完顿感身上有了活力。北大的让人感觉很艺术，但是也很假，不过毕竟相比以往的宣传片有很大的进步。然后，我就找了咱华中科技大学的宣传片，有老版和新版，新版应该是5年以内拍的，顿感差距啊。今年是华中科技大学60年校庆，应该会有新的宣传片出炉，期望有所进步吧。 耶鲁大学《Why I choose Yale》 北京大学宣传片 华中科技大学宣传片（老版） 华中科技大学宣传片（新版）]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/bEe0OlqzZmp_K28WO-GK1Gb4un8/0/da"><img src="http://feedads.g.doubleclick.net/~a/bEe0OlqzZmp_K28WO-GK1Gb4un8/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/bEe0OlqzZmp_K28WO-GK1Gb4un8/1/da"><img src="http://feedads.g.doubleclick.net/~a/bEe0OlqzZmp_K28WO-GK1Gb4un8/1/di" border="0" ismap="true"></img></a></p><p>最近耶鲁大学和北京大学的宣传片对比在微博上很火，对北大也是骂声一片，毕竟人们对北大的期望要更高些。耶鲁大学的宣传片很运动、很活力、很激情，看完顿感身上有了活力。北大的让人感觉很艺术，但是也很假，不过毕竟相比以往的宣传片有很大的进步。然后，我就找了咱华中科技大学的宣传片，有老版和新版，新版应该是5年以内拍的，顿感差距啊。今年是华中科技大学60年校庆，应该会有新的宣传片出炉，期望有所进步吧。<br />
<span id="more-955"></span></p>
<p style="text-align: center;">耶鲁大学《Why I choose Yale》</p>
<p style="text-align: center;"><object width="480" height="400"><param name="movie" value="http://player.youku.com/player.php/sid/XMTU4NzYwMTY4/v.swf"></param><param name="allowFullScreen" value="true"></param><param name="allowscriptaccess" value="never"></param><param name="allownetworking" value="internal"></param><param name="flashvars" value="isShowRelatedVideo=false&showAd=0&show_pre=1&show_next=1&isAutoPlay=false&isDebug=false&UserID=&winType=interior&playMovie=true&MMControl=false&MMout=false&RecordCode=1001,1002,1003,1004,1005,1006,2001,3001,3002,3003,3004,3005,3007,3008,9999" /><embed src="http://player.youku.com/player.php/sid/XMTU4NzYwMTY4/v.swf" type="application/x-shockwave-flash" allowscriptaccess="never" allownetworking="internal" allowfullscreen="true" width="480" height="400" flashvars="isShowRelatedVideo=false&showAd=0&show_pre=1&show_next=1&isAutoPlay=false&isDebug=false&UserID=&winType=interior&playMovie=true&MMControl=false&MMout=false&RecordCode=1001,1002,1003,1004,1005,1006,2001,3001,3002,3003,3004,3005,3007,3008,9999"></embed></object></p>
<p style="text-align: center;">北京大学宣传片</p>
<p style="text-align: center;"><object width="480" height="400"><param name="movie" value="http://player.youku.com/player.php/sid/XMTgwNDc0MzIw/v.swf"></param><param name="allowFullScreen" value="true"></param><param name="allowscriptaccess" value="never"></param><param name="allownetworking" value="internal"></param><param name="flashvars" value="isShowRelatedVideo=false&showAd=0&show_pre=1&show_next=1&isAutoPlay=false&isDebug=false&UserID=&winType=interior&playMovie=true&MMControl=false&MMout=false&RecordCode=1001,1002,1003,1004,1005,1006,2001,3001,3002,3003,3004,3005,3007,3008,9999" /><embed src="http://player.youku.com/player.php/sid/XMTgwNDc0MzIw/v.swf" type="application/x-shockwave-flash" allowscriptaccess="never" allownetworking="internal" allowfullscreen="true" width="480" height="400" flashvars="isShowRelatedVideo=false&showAd=0&show_pre=1&show_next=1&isAutoPlay=false&isDebug=false&UserID=&winType=interior&playMovie=true&MMControl=false&MMout=false&RecordCode=1001,1002,1003,1004,1005,1006,2001,3001,3002,3003,3004,3005,3007,3008,9999"></embed></object></p>
<p style="text-align: center;">华中科技大学宣传片（老版）</p>
<p style="text-align: center;"><object width="480" height="400"><param name="movie" value="http://player.ku6.com/refer/JD9CQJbjgvLsBbT8/v.swf"></param><param name="allowFullScreen" value="true"></param><param name="allowscriptaccess" value="never"></param><param name="allownetworking" value="internal"></param><param name="flashvars" value="" /><embed src="http://player.ku6.com/refer/JD9CQJbjgvLsBbT8/v.swf" type="application/x-shockwave-flash" allowscriptaccess="never" allownetworking="internal" allowfullscreen="true" width="480" height="400" flashvars=""></embed></object></p>
<p style="text-align: center;">华中科技大学宣传片（新版）</p>
<p style="text-align: center;"><object width="480" height="400"><param name="movie" value="http://player.youku.com/player.php/sid/XMjc0MTg5MDQ4/v.swf"></param><param name="allowFullScreen" value="true"></param><param name="allowscriptaccess" value="never"></param><param name="allownetworking" value="internal"></param><param name="flashvars" value="isShowRelatedVideo=false&showAd=0&show_pre=1&show_next=1&isAutoPlay=false&isDebug=false&UserID=&winType=interior&playMovie=true&MMControl=false&MMout=false&RecordCode=1001,1002,1003,1004,1005,1006,2001,3001,3002,3003,3004,3005,3007,3008,9999" /><embed src="http://player.youku.com/player.php/sid/XMjc0MTg5MDQ4/v.swf" type="application/x-shockwave-flash" allowscriptaccess="never" allownetworking="internal" allowfullscreen="true" width="480" height="400" flashvars="isShowRelatedVideo=false&showAd=0&show_pre=1&show_next=1&isAutoPlay=false&isDebug=false&UserID=&winType=interior&playMovie=true&MMControl=false&MMout=false&RecordCode=1001,1002,1003,1004,1005,1006,2001,3001,3002,3003,3004,3005,3007,3008,9999"></embed></object></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/UNltDdmPYNY" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2012/02/13/yale-pku-hust/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2012/02/13/yale-pku-hust/</feedburner:origLink></item>
		<item>
		<title>XP系统Vmware 7安装Linux系统能ping通不能SSH连接的问题</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/i80T_SlXphc/</link>
		<comments>http://www.zhlwish.com/2012/02/11/xp-vmware-7-linux-ping-ssh-samba/#comments</comments>
		<pubDate>Sat, 11 Feb 2012 12:28:42 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=949</guid>
		<description><![CDATA[一直用VMware Workstaion上安装Linux虚拟机进行开发的，安装软件等比Windows上方便很多，因为部署环境也是Linux，因此也避免了编码、换行符等平台兼容的问题，在Linux虚拟机中安装Samba解决文件系统共享的问题，一直都相安无事。 最近为电脑重装了XP，安装好VMware Workstation 7后运行以前的ArchLinux的虚拟机，从发现samba连接不上了，可以在网络邻居的工作组中找到Linux虚拟机，但是共享无法连接，连登录的对话框都不显示。没办法，尝试安装vsftpd，用FTP来共享文件，结果FTP也无法连接，FTP显示已经建立连接，然后就没反应了。后来发现ssh也无法连接，经检查，网络连接正常，也没有安装iptables防火墙，更没有Selinux。并且在同局域网内的其他电脑（Win 7系统）上可以访问samba和vsftpd以及ssh。 后来在终于在http://crazy123.blog.51cto.com/1029610/628287查到有人遇到同样的问题，解决方法为：打开本机（winxp）的设备管理器中找到本机的网卡，打开其属性窗口，在高级标签中找到“offload checksum”将其值置为“Disable”，按确认后，重启电脑就可以通过SSH访问了。 但是，我是Realtek的网卡，高级标签中没有“offload checksum”，更新网卡驱动到最新版本也没有这个选项，经过查找资料，“offload checksum”就是“硬件校验和”，将这项设为“关闭”，重启XP，问题解决了。好像只有Nvidia的网卡才有“offload checksum”这一项，Realtek网卡如下图所示：]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/nbdeiYlA76A6F8K1m1nuM_PiQw8/0/da"><img src="http://feedads.g.doubleclick.net/~a/nbdeiYlA76A6F8K1m1nuM_PiQw8/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/nbdeiYlA76A6F8K1m1nuM_PiQw8/1/da"><img src="http://feedads.g.doubleclick.net/~a/nbdeiYlA76A6F8K1m1nuM_PiQw8/1/di" border="0" ismap="true"></img></a></p><p>一直用VMware Workstaion上安装Linux虚拟机进行开发的，安装软件等比Windows上方便很多，因为部署环境也是Linux，因此也避免了编码、换行符等平台兼容的问题，在Linux虚拟机中安装Samba解决文件系统共享的问题，一直都相安无事。</p>
<p>最近为电脑重装了XP，安装好VMware Workstation 7后运行以前的ArchLinux的虚拟机，从发现samba连接不上了，可以在网络邻居的工作组中找到Linux虚拟机，但是共享无法连接，连登录的对话框都不显示。没办法，尝试安装vsftpd，用FTP来共享文件，结果FTP也无法连接，FTP显示已经建立连接，然后就没反应了。后来发现ssh也无法连接，经检查，网络连接正常，也没有安装iptables防火墙，更没有Selinux。并且在同局域网内的其他电脑（Win 7系统）上可以访问samba和vsftpd以及ssh。<br />
<span id="more-949"></span><br />
后来在终于在<a href="http://crazy123.blog.51cto.com/1029610/628287">http://crazy123.blog.51cto.com/1029610/628287</a>查到有人遇到同样的问题，解决方法为：打开本机（winxp）的设备管理器中找到本机的网卡，打开其属性窗口，在高级标签中找到“offload checksum”将其值置为“Disable”，按确认后，重启电脑就可以通过SSH访问了。</p>
<p>但是，我是Realtek的网卡，高级标签中没有“offload checksum”，更新网卡驱动到最新版本也没有这个选项，经过查找资料，“offload checksum”就是“硬件校验和”，将这项设为“关闭”，重启XP，问题解决了。好像只有Nvidia的网卡才有“offload checksum”这一项，Realtek网卡如下图所示：</p>
<p><img src="http://www.zhlwish.com/wp-content/uploads/2012/02/win-realtek.png" alt="" title="win-realtek" width="404" height="423" class="aligncenter size-full wp-image-950" /></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/i80T_SlXphc" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2012/02/11/xp-vmware-7-linux-ping-ssh-samba/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2012/02/11/xp-vmware-7-linux-ping-ssh-samba/</feedburner:origLink></item>
		<item>
		<title>传智播客创始人张孝祥因病去世</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/Dj4J3KMI6KY/</link>
		<comments>http://www.zhlwish.com/2012/01/03/%e4%bc%a0%e6%99%ba%e6%92%ad%e5%ae%a2%e5%88%9b%e5%a7%8b%e4%ba%ba%e5%bc%a0%e5%ad%9d%e7%a5%a5%e5%9b%a0%e7%97%85%e5%8e%bb%e4%b8%96/#comments</comments>
		<pubDate>Mon, 02 Jan 2012 16:27:51 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>
		<category><![CDATA[成长]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=943</guid>
		<description><![CDATA[昨天在微博上看到张孝祥老师突然病逝，我刚开始搞混了，我以为是孙鑫。孙鑫大家都知道，有一套视频教程讲VC++的，在BT上很火，但是后来不让下载了，说是孙鑫自己办了培训公司，因此不让这类视频在网上传播了。过了一段时间我才意识到我错了，张孝祥最初是讲Java，我Java入门就是看的他的视频，讲Java线程讲得特别清楚，他也创办了培训公司，但是所有的培训视频都在verycd上可以免费下载，全部公开的。顿时让我肃然起敬。 后来读张孝祥在CSDN上的博客，感觉到他的不容易。现如今，计算机科班毕业的大佬们看不起非科班的，就连称谓都有两种：程序猿和程序员。非科班的被认为只会编码，不懂架构，不懂算法的代码民工。而张孝祥做为“代码民工”的培训机构创始人，同样也被大多数人看不起，甚至是贬低，有些公司公然号称不招传智播客的毕业生，但是他还是坚持去做这一份事业。我想说的是，即使是计算机科班的毕业生在编程入门的时候谁不以能有通俗易懂的视频培训课程而感到幸福呢，更何况是所有的视频课程都能通过互联网进行下载，而且免费。这是不仅仅是一种自信，而是一种信仰，一种追求。这样的追求，谁也不能苛责。 中国的IT产业落后国外很多，虽然有多家号称巨牛逼的纳斯达克上市公司，但大多都依赖“墙”而生存。而国内的IT教育与国内外IT的发展就更加脱离甚远了。当今的中国IT事业之幸有张孝祥、孙卫琴这样的一流的入门技术书籍作者和培训师，太多的人因为他们而改变自己的生命，改变整个中国的IT产业。对他们，我们应该致敬。 最后，我想说的是，对于从农村、从家庭条件特别不好的家庭奋斗出来的男人，38岁正是事业像春天里生命旺盛生长的时候，但是张孝祥却突然与世长辞，令人扼腕，我翻看他的博客，翻到这样一篇题目的博文《累病倒了我两次的面试题&#8211;移动用户资费统计系统》，生命只有一次，请善待她吧。在Dian团队的同学们，身体是事业的本钱，坚持锻炼、坚持健康的生活习惯是事业的基础！ 下面是他的一篇博客，不仅是他的故事，也是培训师的心声：《该不该从大学退学的讨论》，看完之后在Dian团队的同学们应该感恩，在大家的大学阶段遇到靠谱的学长带着自己入门，带着自己成长。 ==================================== 关于是直接在大学学本领，还是找一家可靠的培训机构学本领，不同性格、不同家境、不同学校、不同外部环境、不同机遇的人，他们的需求感和选择是不一样的，他们的成才方式也是不同的。另外，我发现那些自己本领不够但又不满意大学教育而迷茫辍学，或大学逃课出来培训的人几乎都是农村出来的，因为从小在缺钱的环境下长大，对拥有金钱的渴望程度更高，更渴望早点挣到钱，早一点摆脱经济上的拮据，早一点扬眉吐气，早一点补贴家庭，所以，他们更憧憬眼前的小成功、小利益，而无法静下心来去耐心追逐长远的宏伟目标，所以，很多农村出来的聪明孩子没有考研，而是大学毕业就迫不及待地出去工作和挣钱了。我就是这种情况的人，我从小就不是一个循规蹈矩和听话的孩子，我没有很强的决心和自制力，我经常自暴自弃，偶尔又能改良归正，我爱折腾，有梦想，但又没有毅力去坚持，我就是一个非常需要拜师学艺的人，但我要找到的一定是真有本领、又愿毫不保守教地教我的师傅。说说我的人生经历吧： 1. 从小生在农村、长在农村，并且属于环境特别不好的家庭。可以说完全是靠老天爷的眷顾而养大的，据说幼儿时候掉进集体公社的1两米深的大粪坑水池里，失去知觉幸亏被一路人发现而捞了上来，已经奄奄一息。 2. 记忆中是从小学三年开始赌钱，每次几分钱的输赢，但特上瘾和痴迷，上学和放学回家的路上都要赌上一会，课间更是不用说，为此挨了家长的不少棍棒，到小学五年级时（那时候五年制小学）居然已经会整天逃课赌钱了，自从那时候因此而被班主任语文老师重重打了一记耳光后，就切身感受了什么叫被打得两眼直冒金花了，这还不算完，第二天还要当着全校师生的面，在庄严的升旗仪式下作全校检讨。 3. 好在小学成绩一向都不错，稀里糊涂地以该小学第一名的成绩考上了当地的重点初中。上初中远离了家长的监管，更加肆无忌惮地赌钱了，地理、历史、体育、音乐等副课不计成绩，老师也不管，干脆直接外出赌钱。一起赌钱的小伙伴不敢逃语文、数学，英语等正课，没了赌友，只能陪着去上课，在课堂上还意犹未尽，钻到课桌底下继续赌，被老师发现拉出来又是几记重重的耳光。初一下学期期末考试成绩一塌糊涂，印象最深的是英语考了9分，这还是因为默写对了a到z之间的一些拼音字母才得到的分数，初一毫无悬念地留级了！我给大人们心目中留下的印象可能非常非常坏吧，我只知道初中是两个学生合伙睡一张床的，一个负责出床垫，另一个负责出被子，有个从小一起长大的小伙伴想和我合伙，可他们家长极力阻止，怕我带坏了小伙伴。 4. 初一复读，幸遇一恩师的关照，学习兴趣上来了，成绩不错，以全校第一名的成绩升入初二，还因成绩第一而被封为全校学习部长，初二上学期还算认真，下学期又开始逃课赌钱了，可见，我这个人很容易受到外界环境的影响，绝对是“近朱者赤， 近墨者黑”的典型，在顺利和良好的环境下，我可以发展得很好，在不利和不良的环境下，我会很颓废和放荡不羁。 5.初二初三一路玩过来，几乎完全忘记了学校是学习的地方，反而觉得学校是能远离家长监管的天堂，临近中考时，一起玩耍的同学都因读书无望而断断续续退学了，没有朋友一起玩了，一个人也玩不起来，只能拿起书本勉强自学吧，现在还记得中考时数学、物理、化学试卷的第一页做了些题，而第二页统统不会，交卷时第二页可谓一层不染。命运还挺照顾我，我居然糊里糊涂考上普通高中了，从所有老师们的言语中，我感受到了他们都很惊讶！但是不知什么原因，我的录取通知书是县里最差最差的八中，而比我成绩差的好些同学都上了好一点的三中。 6.家里走关系花钱让我上了三中，上高中班上60名同学，我成绩倒数几位，并且属于走关系进来的那一类特殊生。不知什么原因，就觉得自己要努力了，尽管许多与初二初三有衔接的数学物理课我都跟不上，甚至想找来初二初三的书本自己补习一下，期中考试居然进步神速，全班第四名，还被提成了小组长。可是，我这个人没有耐力、没有毅力，经不住不良环境的影响，又开始白天在教室睡觉，晚上整宿整宿地赌钱了，成绩又回到了班上倒数几名，班主任问过我一句：“明年你是不是不准备继续读书了？” 7.高二时突然想改变命运，开始废寝忘食地学习起来，居然取得了全年级第二名的好成绩，后来再也无法保持住第二名的成绩了，但成绩一直都还算上等，高中最大的收获就是几乎不听老师的课，全靠自学，自学能力倒是得到了锻炼和提高。因为我们那些老师自身的水平确实很差，问了老师们一些问题，他们总是解释不透彻，只是告诉你标准答案，而说不清为什么，最搞笑的是，每次英语女老师公布题目答案后，还问我答案为什么是这样的。现在回老家遇到一些高中老师，都是高中读书成绩不太好，通过复读勉强上了师范的一些昔日高中同学，他们本身就不太善于学习和总结，课讲不清楚是自然的，确实会耽误和影响一些学生的潜力。那些出类拔萃的学生大学毕业后都留在了大城市，而没有回到小县城去做高中老师。 8.如果相信命运的话，我肯定属于幸运的一类！高考比预期的结果好，居然成了三中的状元，也顺利进了北理工学机械。在北理工大一上学期很认真，很有抱负，因为对所学的功课不感兴趣，下学期又开始颓废了，一学期下来，最高时有两个月连续没进教学区，一日实在无聊想去教室看看，到了物理教室居然没见到一个同学，中午待同学们回宿舍后问原因，答曰早换教室一个多月了。一日数学老师在教室看见我，关心地问道“好久不见了，是不是回家了”。大三大四疯狂打了两年麻将，功课有四门补考，若再补考一门就没学位了，所以，因为学位的压力问题才勉强把大学的功课坚持学完，每次都是考试前一星期疯狂补课。 其实我不是一个自甘堕落和不可救药的人，我也是有理想和抱负的人，只是意志不坚强，遇到挫折就退缩就萎靡，在大学时我想成功，觉得学计算机编程来得最快，所以，自学了c语言，虽然计算机系的研究生说我的c语言水平比他们好些同学可能还高，但我总遇到问题后找不到人请教，也没有足够的上机环境，一个小问题压在心头三个星期得不到解决，最后又开始自暴自弃了，我也曾到中关村软件公司想找个师傅带我，但没有找到，所以又颓废了。我在想，对我这种自持力不强的人，如果有个好的师傅带，有个好的环境，让我先获得独挡一面的能力后，找到自己的兴趣点后，我就会非常努力和投入，就会取得较大的成绩，就能改变一辈子的命运。所以，我对软件培训班有特殊的理解和特殊的情意，那些一帆风顺的人是无法理解的。 最后，推荐是张孝祥最好的朋友郭新明的悼念文章：【追忆张孝祥】 郭新明：一辈子的朋友]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/RTHDBVt5eWQ2f4uEv85KkQ3OXDY/0/da"><img src="http://feedads.g.doubleclick.net/~a/RTHDBVt5eWQ2f4uEv85KkQ3OXDY/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/RTHDBVt5eWQ2f4uEv85KkQ3OXDY/1/da"><img src="http://feedads.g.doubleclick.net/~a/RTHDBVt5eWQ2f4uEv85KkQ3OXDY/1/di" border="0" ismap="true"></img></a></p><p>昨天在微博上看到<a href="http://blog.csdn.net/zhangxiaoxiang" target="_blank">张孝祥</a>老师突然病逝，我刚开始搞混了，我以为是孙鑫。孙鑫大家都知道，有一套视频教程讲VC++的，在BT上很火，但是后来不让下载了，说是孙鑫自己办了培训公司，因此不让这类视频在网上传播了。过了一段时间我才意识到我错了，张孝祥最初是讲Java，我Java入门就是看的他的视频，讲Java线程讲得特别清楚，他也创办了培训公司，但是所有的培训视频都在<a href="http://www.verycd.com/topics/239368/" target="_blank">verycd</a>上可以免费下载，全部公开的。顿时让我肃然起敬。</p>
<p>后来读<a href="http://blog.csdn.net/zhangxiaoxiang" target="_blank">张孝祥在CSDN上的博客</a>，感觉到他的不容易。现如今，计算机科班毕业的大佬们看不起非科班的，就连称谓都有两种：程序猿和程序员。非科班的被认为只会编码，不懂架构，不懂算法的代码民工。而张孝祥做为“代码民工”的培训机构创始人，同样也被大多数人看不起，甚至是贬低，有些公司公然号称不招传智播客的毕业生，但是他还是坚持去做这一份事业。我想说的是，即使是计算机科班的毕业生在编程入门的时候谁不以能有通俗易懂的视频培训课程而感到幸福呢，更何况是所有的视频课程都能通过互联网进行下载，而且免费。这是不仅仅是一种自信，而是一种信仰，一种追求。这样的追求，谁也不能苛责。</p>
<p><span id="more-943"></span></p>
<p>中国的IT产业落后国外很多，虽然有多家号称巨牛逼的纳斯达克上市公司，但大多都依赖“墙”而生存。而国内的IT教育与国内外IT的发展就更加脱离甚远了。当今的中国IT事业之幸有张孝祥、孙卫琴这样的一流的入门技术书籍作者和培训师，太多的人因为他们而改变自己的生命，改变整个中国的IT产业。对他们，我们应该致敬。</p>
<p>最后，我想说的是，对于从农村、从家庭条件特别不好的家庭奋斗出来的男人，38岁正是事业像春天里生命旺盛生长的时候，但是张孝祥却突然与世长辞，令人扼腕，我翻看他的博客，翻到这样一篇题目的博文<a href="http://blog.csdn.net/zhangxiaoxiang/article/details/6304117" target="_blank">《累病倒了我两次的面试题&#8211;移动用户资费统计系统》</a>，生命只有一次，请善待她吧。在<a href="http://weibo.com/diangroup" target="_blank">Dian团队</a>的同学们，身体是事业的本钱，坚持锻炼、坚持健康的生活习惯是事业的基础！</p>
<p>下面是他的一篇博客，不仅是他的故事，也是培训师的心声：<a href="http://blog.csdn.net/z hangxiaoxiang/article/details/7016241" target="_blank">《该不该从大学退学的讨论》</a>，看完之后在<a href="http://weibo.com/diangroup" target="_blank">Dian团队</a>的同学们应该感恩，在大家的大学阶段遇到靠谱的学长带着自己入门，带着自己成长。</p>
<p>====================================</p>
<p>关于是直接在大学学本领，还是找一家可靠的培训机构学本领，不同性格、不同家境、不同学校、不同外部环境、不同机遇的人，他们的需求感和选择是不一样的，他们的成才方式也是不同的。另外，我发现那些自己本领不够但又不满意大学教育而迷茫辍学，或大学逃课出来培训的人几乎都是农村出来的，因为从小在缺钱的环境下长大，对拥有金钱的渴望程度更高，更渴望早点挣到钱，早一点摆脱经济上的拮据，早一点扬眉吐气，早一点补贴家庭，<span style="text-decoration: underline;"><span style="color: #ff0000; text-decoration: underline;">所以，他们更憧憬眼前的小成功、小利益，而无法静下心来去耐心追逐长远的宏伟目标</span></span>，所以，很多农村出来的聪明孩子没有考研，而是大学毕业就迫不及待地出去工作和挣钱了。我就是这种情况的人，我从小就不是一个循规蹈矩和听话的孩子，我没有很强的决心和自制力，我经常自暴自弃，偶尔又能改良归正，我爱折腾，有梦想，但又没有毅力去坚持，我就是一个非常需要拜师学艺的人，但我要找到的一定是真有本领、又愿毫不保守教地教我的师傅。说说我的人生经历吧：</p>
<p>1. 从小生在农村、长在农村，并且属于环境特别不好的家庭。可以说完全是靠老天爷的眷顾而养大的，据说幼儿时候掉进集体公社的1两米深的大粪坑水池里，失去知觉幸亏被一路人发现而捞了上来，已经奄奄一息。</p>
<p>2. 记忆中是从小学三年开始赌钱，每次几分钱的输赢，但特上瘾和痴迷，上学和放学回家的路上都要赌上一会，课间更是不用说，为此挨了家长的不少棍棒，到小学五年级时（那时候五年制小学）居然已经会整天逃课赌钱了，自从那时候因此而被班主任语文老师重重打了一记耳光后，就切身感受了什么叫被打得两眼直冒金花了，这还不算完，第二天还要当着全校师生的面，在庄严的升旗仪式下作全校检讨。</p>
<p>3. 好在小学成绩一向都不错，稀里糊涂地以该小学第一名的成绩考上了当地的重点初中。上初中远离了家长的监管，更加肆无忌惮地赌钱了，地理、历史、体育、音乐等副课不计成绩，老师也不管，干脆直接外出赌钱。一起赌钱的小伙伴不敢逃语文、数学，英语等正课，没了赌友，只能陪着去上课，在课堂上还意犹未尽，钻到课桌底下继续赌，被老师发现拉出来又是几记重重的耳光。初一下学期期末考试成绩一塌糊涂，印象最深的是英语考了9分，这还是因为默写对了a到z之间的一些拼音字母才得到的分数，初一毫无悬念地留级了！我给大人们心目中留下的印象可能非常非常坏吧，我只知道初中是两个学生合伙睡一张床的，一个负责出床垫，另一个负责出被子，有个从小一起长大的小伙伴想和我合伙，可他们家长极力阻止，怕我带坏了小伙伴。</p>
<p>4. 初一复读，幸遇一恩师的关照，学习兴趣上来了，成绩不错，以全校第一名的成绩升入初二，还因成绩第一而被封为全校学习部长，初二上学期还算认真，下学期又开始逃课赌钱了，可见，我这个人很容易受到外界环境的影响，绝对是“近朱者赤， 近墨者黑”的典型，在顺利和良好的环境下，我可以发展得很好，在不利和不良的环境下，我会很颓废和放荡不羁。</p>
<p>5.初二初三一路玩过来，几乎完全忘记了学校是学习的地方，反而觉得学校是能远离家长监管的天堂，临近中考时，一起玩耍的同学都因读书无望而断断续续退学了，没有朋友一起玩了，一个人也玩不起来，只能拿起书本勉强自学吧，现在还记得中考时数学、物理、化学试卷的第一页做了些题，而第二页统统不会，交卷时第二页可谓一层不染。命运还挺照顾我，我居然糊里糊涂考上普通高中了，从所有老师们的言语中，我感受到了他们都很惊讶！但是不知什么原因，我的录取通知书是县里最差最差的八中，而比我成绩差的好些同学都上了好一点的三中。</p>
<p>6.家里走关系花钱让我上了三中，上高中班上60名同学，我成绩倒数几位，并且属于走关系进来的那一类特殊生。不知什么原因，就觉得自己要努力了，尽管许多与初二初三有衔接的数学物理课我都跟不上，甚至想找来初二初三的书本自己补习一下，期中考试居然进步神速，全班第四名，还被提成了小组长。可是，我这个人没有耐力、没有毅力，经不住不良环境的影响，又开始白天在教室睡觉，晚上整宿整宿地赌钱了，成绩又回到了班上倒数几名，班主任问过我一句：“明年你是不是不准备继续读书了？”</p>
<p>7.高二时突然想改变命运，开始废寝忘食地学习起来，居然取得了全年级第二名的好成绩，后来再也无法保持住第二名的成绩了，但成绩一直都还算上等，高中最大的收获就是几乎不听老师的课，全靠自学，自学能力倒是得到了锻炼和提高。因为我们那些老师自身的水平确实很差，问了老师们一些问题，他们总是解释不透彻，只是告诉你标准答案，而说不清为什么，最搞笑的是，每次英语女老师公布题目答案后，还问我答案为什么是这样的。现在回老家遇到一些高中老师，都是高中读书成绩不太好，通过复读勉强上了师范的一些昔日高中同学，他们本身就不太善于学习和总结，课讲不清楚是自然的，确实会耽误和影响一些学生的潜力。那些出类拔萃的学生大学毕业后都留在了大城市，而没有回到小县城去做高中老师。</p>
<p>8.如果相信命运的话，我肯定属于幸运的一类！高考比预期的结果好，居然成了三中的状元，也顺利进了北理工学机械。在北理工大一上学期很认真，很有抱负，因为对所学的功课不感兴趣，下学期又开始颓废了，一学期下来，最高时有两个月连续没进教学区，一日实在无聊想去教室看看，到了物理教室居然没见到一个同学，中午待同学们回宿舍后问原因，答曰早换教室一个多月了。一日数学老师在教室看见我，关心地问道“好久不见了，是不是回家了”。大三大四疯狂打了两年麻将，功课有四门补考，若再补考一门就没学位了，所以，因为学位的压力问题才勉强把大学的功课坚持学完，每次都是考试前一星期疯狂补课。</p>
<p><span style="color: #ff0000;">其实我不是一个自甘堕落和不可救药的人，我也是有理想和抱负的人，只是意志不坚强，遇到挫折就退缩就萎靡</span>，在大学时我想成功，觉得学计算机编程来得最快，所以，自学了c语言，虽然计算机系的研究生说我的c语言水平比他们好些同学可能还高，但我总遇到问题后找不到人请教，也没有足够的上机环境，一个小问题压在心头三个星期得不到解决，最后又开始自暴自弃了，我也曾到中关村软件公司想找个师傅带我，但没有找到，所以又颓废了。我在想，<strong><span style="color: #ff0000;">对我这种自持力不强的人，如果有个好的师傅带，有个好的环境，让我先获得独挡一面的能力后，找到自己的兴趣点后，我就会非常努力和投入，就会取得较大的成绩，就能改变一辈子的命运</span></strong>。所以，我对软件培训班有特殊的理解和特殊的情意，那些一帆风顺的人是无法理解的。</p>
<p>最后，推荐是张孝祥最好的朋友郭新明的悼念文章：<a href="http://news.csdn.net/a/20120104/310084.html" target="_blank">【追忆张孝祥】 郭新明：一辈子的朋友</a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/Dj4J3KMI6KY" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2012/01/03/%e4%bc%a0%e6%99%ba%e6%92%ad%e5%ae%a2%e5%88%9b%e5%a7%8b%e4%ba%ba%e5%bc%a0%e5%ad%9d%e7%a5%a5%e5%9b%a0%e7%97%85%e5%8e%bb%e4%b8%96/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2012/01/03/%e4%bc%a0%e6%99%ba%e6%92%ad%e5%ae%a2%e5%88%9b%e5%a7%8b%e4%ba%ba%e5%bc%a0%e5%ad%9d%e7%a5%a5%e5%9b%a0%e7%97%85%e5%8e%bb%e4%b8%96/</feedburner:origLink></item>
		<item>
		<title>骗人的美国主机服务商WebHostingPad</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/VKElzEh4ECg/</link>
		<comments>http://www.zhlwish.com/2011/12/15/webhostingpad-cheater/#comments</comments>
		<pubDate>Wed, 14 Dec 2011 17:31:54 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=929</guid>
		<description><![CDATA[我终于忍不住要写这篇博客，奉劝想省钱的朋友们：“便宜无好货”，而且不要被所谓的“华人”给骗了。 我是在找国外主机的时候发现WebHostingPad的，因为有介绍说创始人是华人，因此多了一份好感。价钱比较便宜，2-3美元一个月，而且还可以绑定无限个域名，其他的限制条件（如空间、文件数、流量）基本都是不限制，这对于我这个一直用国内主机的人来说是很兴奋的。大家都知道国内的空间总是限你的文件数目、数据库的个数等等等等，一遍又一遍的强奸用户。而且WebHostingPad还承诺一个月不满意就退款。 事实证明，一个月之内的确没有任何问题，网站速度也不错。当一个月满了，过了几天之后，帐号被禁用了。客服说CPU使用太多，我艹，我就一个WordPress，而且每天的独立IP也就70-100，这样也CPU使用太多？ 我以为被挂马了，我把WordPress和数据下载下来，在本地分析之后，发现没有被挂马，一切正常，普通PC上访问一点问题都没有。我给客户说应该是你们的服务有问题，他说让我卸掉WordPress插件，于是我按照客服的要求，卸载了所有的WordPress插件，他们说CPU依然使用过多。 又按他们的要求将WordPress降到了旧的2.8版本，CPU还是使用过多。这让我很无语了。WebHostingPad用的是小霸王么、阿童木么？连个WordPress每天70-100的访问量都承受不了？ 后来，我在找到下面一些文章： WebHostingPad是不是骗子？ 谨慎：注册Webhostingpad免费域名 美国主机WebHostingPad的最大文件数量限制 美国主机WebHostingPad五个月评价 我突然醒悟了，难道是一个月退款期过了就想把我赶走么？找了客服，总是一遍又一遍说我的WordPress有问题，那为什么之前的一个月就一点问题都没有呢？我感觉，我应该被骗了。 下面是北山美国主机评论的原话，希望各位朋友警惕： 提示：经过几个月的使用和体验，WebHostingPad虽然便宜，但限制比较多，而且从商业的角度来说，存在信誉的问题，不建议购买WebHostingPad主机。]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/ayK7osq3EUTYFQFrxQpHRXAG1to/0/da"><img src="http://feedads.g.doubleclick.net/~a/ayK7osq3EUTYFQFrxQpHRXAG1to/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/ayK7osq3EUTYFQFrxQpHRXAG1to/1/da"><img src="http://feedads.g.doubleclick.net/~a/ayK7osq3EUTYFQFrxQpHRXAG1to/1/di" border="0" ismap="true"></img></a></p><p>我终于忍不住要写这篇博客，奉劝想省钱的朋友们：“便宜无好货”，而且不要被所谓的“华人”给骗了。</p>
<p>我是在找国外主机的时候发现WebHostingPad的，因为有介绍说创始人是华人，因此多了一份好感。价钱比较便宜，2-3美元一个月，而且还可以绑定无限个域名，其他的限制条件（如空间、文件数、流量）基本都是不限制，这对于我这个一直用国内主机的人来说是很兴奋的。大家都知道国内的空间总是限你的文件数目、数据库的个数等等等等，一遍又一遍的强奸用户。而且WebHostingPad还承诺一个月不满意就退款。</p>
<p>事实证明，一个月之内的确没有任何问题，网站速度也不错。当一个月满了，过了几天之后，帐号被禁用了。客服说CPU使用太多，我艹，我就一个WordPress，而且每天的独立IP也就70-100，这样也CPU使用太多？<br />
<span id="more-929"></span><br />
我以为被挂马了，我把WordPress和数据下载下来，在本地分析之后，发现没有被挂马，一切正常，普通PC上访问一点问题都没有。我给客户说应该是你们的服务有问题，他说让我卸掉WordPress插件，于是我按照客服的要求，卸载了所有的WordPress插件，他们说CPU依然使用过多。</p>
<p>又按他们的要求将WordPress降到了旧的2.8版本，CPU还是使用过多。这让我很无语了。WebHostingPad用的是<a href="http://baike.baidu.com/view/601770.htm#sub5594349">小霸王</a>么、<a href="http://baike.baidu.com/view/21936.htm#sub7031120">阿童木</a>么？连个WordPress每天70-100的访问量都承受不了？</p>
<p>后来，我在找到下面一些文章：</p>
<ol>
<li><a href="http://www.beishan.info/webhostingpad/20090511/webhostingpad-scam-or-not.html" target="_blank">WebHostingPad是不是骗子？</a></li>
<li><a href="http://www.beishan.info/webhostingpad/20100323/stay-away-webhostingpad-free-domain.html" target="_blank">谨慎：注册Webhostingpad免费域名</a></li>
<li><a href="http://www.beishan.info/webhostingpad/20090526/webhostingpad-files-limit.html" target="_blank">美国主机WebHostingPad的最大文件数量限制</a></li>
<li><a href="http://www.beishan.info/webhostingpad/20090528/webhostingpad-five-month-review.html" target="_blank">美国主机WebHostingPad五个月评价</a></li>
</ol>
<p>我突然醒悟了，难道是一个月退款期过了就想把我赶走么？找了客服，总是一遍又一遍说我的WordPress有问题，那为什么之前的一个月就一点问题都没有呢？我感觉，我应该被骗了。</p>
<p>下面是<a href="http://www.beishan.info/">北山美国主机评论</a>的原话，希望各位朋友警惕：</p>
<p><strong>提示：经过几个月的使用和体验，WebHostingPad虽然便宜，但限制比较多，而且从商业的角度来说，存在信誉的问题，不建议购买WebHostingPad主机。</strong></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/VKElzEh4ECg" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/12/15/webhostingpad-cheater/feed/</wfw:commentRss>
		<slash:comments>11</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/12/15/webhostingpad-cheater/</feedburner:origLink></item>
		<item>
		<title>X Window System简介</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/LVa7hBmkQYM/</link>
		<comments>http://www.zhlwish.com/2011/12/15/x-window-system/#comments</comments>
		<pubDate>Wed, 14 Dec 2011 16:39:48 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[ubuntu]]></category>
		<category><![CDATA[x window]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=922</guid>
		<description><![CDATA[历史 1984年，MIT开始研究X Window System，用于在Unix上支持GUI界面，X Window System研究时是作为应用软件进行开发的，而不是操作系统。而且X Window System是作为架构规范进行研究，因此需要人和组织对其进行实现和包装（和linux一样，要有发行版）。 1987年，X版本更新到X11，这一版有非常明显的进步，因此后面X Window System也被称为X11，X11有通过网络功能访问GUI界面的功能， 1994年，X11R6发布，后来的架构都基于此版本，1995年发布X11R6.3。 前面提到X Window System是作为架构规范进行研究的，需要有人去实现，而1992年开始的XFree86项目就是这样一个被广泛使用的实现，名称来源于X+Free+X86架构。 2004年的时候，XFree86不在以GPL协议发布，而是另外成立了公司。X.Org基金会就从XFree86的派生出了另一个窗口系统，称为X.Org Server的X Window System。 现在X11最新的版本是X11R7.6，X.Org发布的X Window实现最新版本为1.11。 因此，我们称X、X Window、X11、xf86都是指代X Window System。 X的作用 X能为GUI环境提供基本的框架：在屏幕上描绘、体现图像与移动程序窗口，同时也受理、运行、及管理电脑与鼠标、键盘的交互程序。不过，X并没有管辖到用户界面的部份（可以理解为界面样式，如gnome和kde就外观完全不同），而是由其他以X为基础的界面实现来负责，也因为如此，以X为基础环境所开发成的视觉样式非常地多；不同的程序可能有完全不同的用户界面。 X的架构 X Window System由X Server（服务器）和X Client（客户端）两部分组成。X采行C/S的架构模型，由一个X服务器与多个X客户端程序进行通讯，服务器接受对于图形输出（窗口）的请求并反馈用户输入（键盘、鼠标、触摸屏），服务器可能是一个能显示到其他显示系统的应用程序，也可能是控制某个PC的视频输出的系统程序，也可能是个特殊硬件。前面提到的Xorg基金会发布的X.org Server就是一个服务端。 Linux系统在/etc/sysconfig目录中有键盘、鼠标等硬件的配置文件，但是因为X Server只是一个应用软件，因此他有自己的配置文件。X Server只有在run level 3的时候才会启动，因此只有在这个时候才会去用这些配置文件。 X的一大特点在于“网络透明性”：应用程序（“客户端”应用程序）所运行的机器，不一定是用户本地的机器（显示的“服务器”）。X中所提及的“客户端”和“服务器”等字眼用词也经常与人们一般想定的相反，“服务器”反而是在用户本地端的自有机器上运行，“客户端”是运行与远程服务器上的。客户端和服务器可以在同一台计算机上，也可以不是，或许其架构和操作系统也不同，但都能运行。 &#8230; <a href="http://www.zhlwish.com/2011/12/15/x-window-system/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/3BUx6ams8Ezz2P-yVq2iFRfW1eM/0/da"><img src="http://feedads.g.doubleclick.net/~a/3BUx6ams8Ezz2P-yVq2iFRfW1eM/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/3BUx6ams8Ezz2P-yVq2iFRfW1eM/1/da"><img src="http://feedads.g.doubleclick.net/~a/3BUx6ams8Ezz2P-yVq2iFRfW1eM/1/di" border="0" ismap="true"></img></a></p><p><strong>历史</strong></p>
<p>1984年，MIT开始研究X Window System，用于在Unix上支持GUI界面，X Window System研究时是作为应用软件进行开发的，而不是操作系统。而且X Window System是作为架构规范进行研究，因此需要人和组织对其进行实现和包装（和linux一样，要有发行版）。</p>
<p>1987年，X版本更新到X11，这一版有非常明显的进步，因此后面X Window System也被称为X11，X11有通过网络功能访问GUI界面的功能，<br />
<span id="more-922"></span><br />
1994年，X11R6发布，后来的架构都基于此版本，1995年发布X11R6.3。</p>
<p>前面提到X Window System是作为架构规范进行研究的，需要有人去实现，而1992年开始的XFree86项目就是这样一个被广泛使用的实现，名称来源于X+Free+X86架构。</p>
<p>2004年的时候，XFree86不在以GPL协议发布，而是另外成立了公司。X.Org基金会就从XFree86的派生出了另一个窗口系统，称为X.Org Server的X Window System。</p>
<p>现在X11最新的版本是X11R7.6，X.Org发布的X Window实现最新版本为1.11。</p>
<p>因此，我们称X、X Window、X11、xf86都是指代X Window System。</p>
<p><strong>X的作用</strong></p>
<p>X能为GUI环境提供基本的框架：在屏幕上描绘、体现图像与移动程序窗口，同时也受理、运行、及管理电脑与鼠标、键盘的交互程序。不过，X并没有管辖到用户界面的部份（可以理解为界面样式，如gnome和kde就外观完全不同），而是由其他以X为基础的界面实现来负责，也因为如此，以X为基础环境所开发成的视觉样式非常地多；不同的程序可能有完全不同的用户界面。</p>
<p><strong>X的架构</strong></p>
<p>X Window System由X Server（服务器）和X Client（客户端）两部分组成。X采行C/S的架构模型，由一个X服务器与多个X客户端程序进行通讯，服务器接受对于图形输出（窗口）的请求并反馈用户输入（键盘、鼠标、触摸屏），服务器可能是一个能显示到其他显示系统的应用程序，也可能是控制某个PC的视频输出的系统程序，也可能是个特殊硬件。前面提到的Xorg基金会发布的X.org Server就是一个服务端。</p>
<p><img class="aligncenter size-medium wp-image-940" title="X Client与X Sever" src="http://www.zhlwish.com/wp-content/uploads/2011/12/250px-X_client_server_example_zh-cn.svg_-177x300.png" alt="" width="177" height="300" /></p>
<p>Linux系统在/etc/sysconfig目录中有键盘、鼠标等硬件的配置文件，但是因为X Server只是一个应用软件，因此他有自己的配置文件。X Server只有在run level 3的时候才会启动，因此只有在这个时候才会去用这些配置文件。</p>
<p>X的一大特点在于“网络透明性”：应用程序（“客户端”应用程序）所运行的机器，不一定是用户本地的机器（显示的“服务器”）。X中所提及的“客户端”和“服务器”等字眼用词也经常与人们一般想定的相反，“服务器”反而是在用户本地端的自有机器上运行，“客户端”是运行与远程服务器上的。客户端和服务器可以在同一台计算机上，也可以不是，或许其架构和操作系统也不同，但都能运行。</p>
<p><strong>X Window Manager</strong></p>
<p>这是一个特殊的X Client，负责管理所有的X Client。X Client之间是相互平等的，相互也不知道对方的存在。因此需要有个Window Manager对他们进行管理。主要负责：</p>
<ol>
<li>提供许多的配置选项，包括任务栏、背景桌面的设置等等；</li>
<li>管理虚拟桌面 (virtual desktop)，Ubuntu里面称为工作区；</li>
<li>提供窗口控制参数，如窗口的大小、重叠次序、窗口移动、窗口最小化等。</li>
</ol>
<p>Gnome，KDE，XFCE就是所谓的X Window Manager</p>
<p>因此，在一台Linux机器上，我们必须要安装Xorg的X Server，才能接收到键盘等交互设备的输入、才能在窗口上绘制图形界面。为了更好的管理图形界面，于是还需要安装Gnome这样的X Window Manager。</p>
<p><strong>Display Manager</strong></p>
<p>如果已经登录了，在文字界面下输入startx就可以启动X图形系统。但是一般的图形界面linux系统会在系统启动后让你进行登录，这个登录界面就是Display Manager了，主要提供登录的功能，并且载入用户选择的X Window Manager的配置（我们可以在ubuntu启动的时候选择使用Gnome3还是Gnome Classical，或者可能还有Xfce，如果你安装了XFCE的话）。</p>
<p>gdm就是Gnome Display Manager了。</p>
<p><strong>启动X Window System的流程</strong></p>
<p><strong></strong>文字界面下使用startx启动X图形系统，startx实际上是一个Shell脚本，其作用是使用当前用户默认的X Server的配置启动X Window System。startx实际上是通过执行xinit来启动X图形系统的。</p>
<p>X Server的启动参数才/etc/X11/xinit/xserverrc中，X Client的参数在/etc/X11/xinit/xinitrc。具体的参数另行撰文。</p>
<p><strong>参考</strong></p>
<ol>
<li><a title="维基百科：X.org" href="http://zh.wikipedia.org/wiki/X.Org_%E6%9C%8D%E5%8A%A1%E5%99%A8" target="_blank">维基百科：X.org</a></li>
<li><a title="维基百科：X Window" href="http://zh.wikipedia.org/wiki/X_Window%E7%B3%BB%E7%B5%B1" target="_blank">维基百科：X Window</a></li>
</ol>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/LVa7hBmkQYM" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/12/15/x-window-system/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/12/15/x-window-system/</feedburner:origLink></item>
		<item>
		<title>《设计与生存》读书笔记</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/AnIlNHULbVs/</link>
		<comments>http://www.zhlwish.com/2011/11/12/%e8%ae%be%e8%ae%a1%e4%b8%8e%e7%94%9f%e5%ad%98/#comments</comments>
		<pubDate>Sat, 12 Nov 2011 09:51:12 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>
		<category><![CDATA[管理]]></category>
		<category><![CDATA[读书]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=836</guid>
		<description><![CDATA[题注：本书的标题全名为《设计与生存————一位IT设计管理人员20年的经历与感悟》 很久以前就看到团队藏书里面有一本书叫《设计与生存》，2006年出版，时隔今日已5年，在半年就技术升级的IT世界，已经算是老龄了，所以给我最初的映像是装帧土气、历史久远，“历史久远”绝对不是褒义。不过副标题“一位IT设计管理人员20年的经历与感悟”却是引起了我的注意，人生能有几个二十年呢？于是我拿起这本其貌不扬的书快速地浏览了一下，顿时就被吸引了。看完第一章就对作者马宁伟先生的奋进、执着和思考由衷的敬佩。我立马想到新浪微博上找这个作者，可惜看到的是马先生因为肝癌已经离我们远去，我根据网上的资料推测应该是2011年初。在此以表达对马宁伟先生的缅怀。马先生的简介http://baike.baidu.com/view/1885686.htm。 作者77年进入宿迁无线电厂工作，因为文革期间很多大学教授到被下放到这里，于是作者有幸跟随大师学习和工作。不过正如作者自己说的“师傅领进门，修行在个人”，作者依靠自己“勤奋”和“爱动脑筋”，成为骨干。1985年在国企非常有前瞻性的开始做一些研究上的东西，虽然技术资料很少，获得极为不便，但是仍然坚持读英文原版书。我想到团队藏书里面整整二三十本原版书居然没有任何一个人读，感觉万分惭愧。之前听华域王建平总裁讲座，说“你们生逢盛世”，当时毫无感触。阅读了马宁伟先生的文字，顿时感同身受。 这本书告诉我们的不仅是为人处世、管理团队的经验，更是在讲述那个时代的精神——我们这个时代已经丢掉的勤奋、专研、踏实、负责的精神。 作者的语言非常的朴素，甚至非常口语化，和作者自称只有“电大”的学历到是很相称，但是语言朴素却掩盖不了道理的深邃，掩盖不了思想的光芒。下面是摘抄的一些句子，大部分是我感同身受的道理。 写技术论文不仅使自己进一步理清思路，也会加深对问题的理解，因为你写的时候才会发现，有些问题原理自己也和不清楚，给别人讲课也是如此。写和讲两件事都是看起来实在帮别人，实际上也是与己有益的事。后来，我对工程师的要求都是要会做，会写和会讲。 成功的转折来自于对社会、行业、自身的了解和积极的准备，来自于忧患意识，这样才能抓住时机。 （计算机）……原本大家都清楚这只是一种工具，是次要因素，但实际上却成了正真的一道逾越不过去的墙，结果真正重要的工程师的思维分析能力、实际经验反而无用武之地。 电视是一个给人带来娱乐的好东西，但是看长了也是使人弱智的东西，因为从人的接收能力来讲，图像比文字来的容易得多，电视看多了，脑筋就动的少，脑力自然不发达。而读文字的时候需要你思考，才能理解；需要从文字中将图形在脑中成像，这就锻炼了脑力。 一个好的设计师，一定要用心做事，技术上的事是躲不过去的，今天没有仔细去合算上下两种工作极限的状况，明天一定会让你十倍的头痛。“天道酬勤”讲的就是这个道理。 我们那时能凝聚一批工程师，在人员流动率比较高的深圳保持了人员稳定，并且快速出了成果和人才，今天回头看，主要靠的是三条：第一是公司有一定的知名度；第二是大家有事做，有技术学；第三是部门风气正，奖罚分明。 在很多管理细节上，并不要花钱，就是需要有人以“服务”的心态去做。而传统的行政人事部门，工作的出发点就是“管”，其实真要管的东西不多，多向前走一步，帮人忙的事情倒是很多，以服务的心态去做事，别人的感觉就会舒服了，做事效率自然就高了。 （得人心者能成事）……我的管理原则一直是用能人，绝不会因个人的喜好去埋没人才，一个员工在他进门的时候会看他的文凭和工作背景，进公司后只会看他的实际能力。 不是每个技术好的工程师都能做好管理。 展示产品形象的要素： 市场定位的用户群体 提炼三条左右的卖点 在同类产品中的功能优势 产品技术方面所达到的高度（国内先进水平，还是什么水平） 目前研发进展 何时可以量产 由于长年的阅读习惯，我读书的速度是很快的，一夜可以读完厚厚的一本。基本上我采用的是第一遍快速地读，记下大致内容，等到用时就知道这个问题在那本书上谈到过，在拿出来细看。 （建立企业文化的方法之一）……使用漫画家郑辛遥的哲理漫画做辅助，“生活就是这样充满遗憾，当你擦玻璃的时候，脏的东西总是在另一面”，“生气的后果永远比生气的原因严重，擦伤引起的争吵几乎总是以刺伤搞结束” （企业文化）……不愿意做技术传承的工程师，不能在这个中心工作，这就是我们的一个“天条”。 （企业文化）……团队合作来源于体育界的球队，要点是个人各就各位，分工合作，而不是几个人做同样的事。 （组织架构、职责划分）……我的体会是职责划分越清楚，越利于项目组成员的执行，做事效率也越高。不会出现一件事多人重复做，或者一件事没有人做的情况。有一些公司不愿意在职责划分上花些时间将其定义清楚，而是一味地要员工“主动”，那不是一个好的做法，有时也会造成低效率。“主动”仅应该体现在两人职责的交接处，没发写清楚的细节部分。“做我该做，说我该说”才是一个有序的团队。 师傅领进门，修行在个人——大事是靠培养出来的吗？大画家、大作家、设计大师都是初期得到引导，后期自身修炼的结果。 有测试表明：创造性思维的能力强的人，智商只是中等水平。 一个团队的知识互补是重要的。 对于工程师来说，一个共同的需求就是英文的要求。凡是想做好技术的工程师，英文是必需的，因为大部分深层的技术资料都是英文的。 情商（EQ）是只一个人对情绪的自我认知、自我控制、自我驱策能力以及对他人反馈能力和情绪的识别这5个方面的能力。 （应届毕业生的选择）……“大水出大鱼”，刚毕业的学生要尽可能进大公司。即使你打定注意要自己创业，这也是一条很好的起步之路。知名外企和一流的台资大公司都有相当完善的用人制度、各种管理方法和各种作业流程，做事的观念和方法与学校中收到的教育和主流媒体宣传的也大不相同，对人的评价体系就大不相同。进入这些企业是极好的改变自己的机会，也是给自己一个崭新的视角去看问题。 最重要的就是选择适合你自己的个性、职业发展的公司，选择于你最为重视的价值观相一致的企业，选择植根你内心的人生兴趣相一致的专业。 技术人员书读多了，整天用的是逻辑思维，自然是敏感而多疑，执着甚而固执；想得到别人承认，却又表现得满不在乎；希望碰到知己者，又常感怀才不遇。 有人说，这个世界上人类已经没有共同的理想。其实不然，受过高等教育的研发工程师心中始终埋藏着公平、民主、自由的社会理想，一旦有机会就会表现出来。 我比较推崇的管理方法是职责明晰、流程清楚、方法规范、公平竞争。从管理风格上我喜欢直面事实，不绕弯说出自己的观点，尤其是对技术问题。但这种管理风格对心理脆弱的人效果不好……，所以我会避开这类人。 管理靠细致，对作业面的所有工程师，“心细如发”可能是共同的个性特质要求。……（粗心的表现）……分析下来，也许并不是不负责任，而是心粗。为此，我曾对两位屡教不改的粗心工厂是做过一种培训，就是每天话一小时，让他们吧一碗黑白混合的芝麻分开。……我们还举行用筷子同时夹起三粒生花生米的训练。 建立checklist机制。 在高速运行的企业，最好的报告是“让上司走出电梯前就能看完的报告”。怎样可以做到这样的效果？这就需要反其道而行之，先写结论，在写论证过程，附相关数据表格。 软件行业有一句著名的格言“进来的是垃圾，出去的还是垃圾”。意思是不把工作要求了解清楚，就想当然的做下去，结果一定是产出一堆无用的东西。 &#8230; <a href="http://www.zhlwish.com/2011/11/12/%e8%ae%be%e8%ae%a1%e4%b8%8e%e7%94%9f%e5%ad%98/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/YLm04NyIsao0bydNw_2GaqhOQsw/0/da"><img src="http://feedads.g.doubleclick.net/~a/YLm04NyIsao0bydNw_2GaqhOQsw/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/YLm04NyIsao0bydNw_2GaqhOQsw/1/da"><img src="http://feedads.g.doubleclick.net/~a/YLm04NyIsao0bydNw_2GaqhOQsw/1/di" border="0" ismap="true"></img></a></p><p><strong>题注：</strong>本书的标题全名为《设计与生存————一位IT设计管理人员20年的经历与感悟》</p>
<p>很久以前就看到团队藏书里面有一本书叫《设计与生存》，2006年出版，时隔今日已5年，在半年就技术升级的IT世界，已经算是老龄了，所以给我最初的映像是<strong>装帧土气、历史久远</strong>，“历史久远”绝对不是褒义。不过副标题“一位IT设计管理人员20年的经历与感悟”却是引起了我的注意，人生能有几个二十年呢？于是我拿起这本其貌不扬的书快速地浏览了一下，顿时就被吸引了。看完第一章就对作者马宁伟先生的奋进、执着和思考由衷的敬佩。我立马想到新浪微博上找这个作者，可惜看到的是马先生因为肝癌已经离我们远去，我根据网上的资料推测应该是2011年初。在此以表达对马宁伟先生的缅怀。马先生的简介<a href="http://baike.baidu.com/view/1885686.htm">http://baike.baidu.com/view/1885686.htm</a>。<br />
<span id="more-836"></span></p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/11/476107c8jw1dn03hsc5jrj.jpg" rel="lightbox[836]"><img class="size-medium wp-image-838 aligncenter" title="设计与生存——一位IT设计管理人员20年的经历与感悟" src="http://www.zhlwish.com/wp-content/uploads/2011/11/476107c8jw1dn03hsc5jrj-190x300.jpg" alt="" width="190" height="300" /></a></p>
<p>作者77年进入宿迁无线电厂工作，因为文革期间很多大学教授到被下放到这里，于是作者有幸跟随大师学习和工作。不过正如作者自己说的“师傅领进门，修行在个人”，作者依靠自己“勤奋”和“爱动脑筋”，成为骨干。1985年在国企非常有前瞻性的开始做一些研究上的东西，虽然技术资料很少，获得极为不便，但是仍然坚持读英文原版书。我想到团队藏书里面整整二三十本原版书居然没有任何一个人读，感觉万分惭愧。之前听华域王建平总裁讲座，说“你们生逢盛世”，当时毫无感触。阅读了马宁伟先生的文字，顿时感同身受。</p>
<p>这本书告诉我们的不仅是为人处世、管理团队的经验，更是在讲述那个时代的精神——我们这个时代已经丢掉的勤奋、专研、踏实、负责的精神。</p>
<p>作者的语言非常的朴素，甚至非常口语化，和作者自称只有“电大”的学历到是很相称，但是语言朴素却掩盖不了道理的深邃，掩盖不了思想的光芒。下面是摘抄的一些句子，大部分是我感同身受的道理。</p>
<hr />
<ol>
<li>写技术论文不仅使自己进一步理清思路，也会加深对问题的理解，因为你写的时候才会发现，有些问题原理自己也和不清楚，给别人讲课也是如此。写和讲两件事都是看起来实在帮别人，实际上也是与己有益的事。后来，我对工程师的要求都是要会做，会写和会讲。</li>
<li>成功的转折来自于对社会、行业、自身的了解和积极的准备，来自于忧患意识，这样才能抓住时机。</li>
<li>（计算机）……原本大家都清楚这只是一种工具，是次要因素，但实际上却成了正真的一道逾越不过去的墙，结果真正重要的工程师的思维分析能力、实际经验反而无用武之地。</li>
<li>电视是一个给人带来娱乐的好东西，但是看长了也是使人弱智的东西，因为从人的接收能力来讲，图像比文字来的容易得多，电视看多了，脑筋就动的少，脑力自然不发达。而读文字的时候需要你思考，才能理解；需要从文字中将图形在脑中成像，这就锻炼了脑力。</li>
<li>一个好的设计师，一定要用心做事，技术上的事是躲不过去的，今天没有仔细去合算上下两种工作极限的状况，明天一定会让你十倍的头痛。“天道酬勤”讲的就是这个道理。</li>
<li>我们那时能凝聚一批工程师，在人员流动率比较高的深圳保持了人员稳定，并且快速出了成果和人才，今天回头看，主要靠的是三条：第一是公司有一定的知名度；第二是大家有事做，有技术学；第三是部门风气正，奖罚分明。</li>
<li>在很多管理细节上，并不要花钱，就是需要有人以“服务”的心态去做。而传统的行政人事部门，工作的出发点就是“管”，其实真要管的东西不多，多向前走一步，帮人忙的事情倒是很多，以服务的心态去做事，别人的感觉就会舒服了，做事效率自然就高了。</li>
<li>（得人心者能成事）……我的管理原则一直是用能人，绝不会因个人的喜好去埋没人才，一个员工在他进门的时候会看他的文凭和工作背景，进公司后只会看他的实际能力。</li>
<li>不是每个技术好的工程师都能做好管理。</li>
<li>展示产品形象的要素：
<ol>
<li>市场定位的用户群体</li>
<li>提炼三条左右的卖点</li>
<li>在同类产品中的功能优势</li>
<li>产品技术方面所达到的高度（国内先进水平，还是什么水平）</li>
<li>目前研发进展</li>
<li>何时可以量产</li>
</ol>
</li>
<li>由于长年的阅读习惯，我读书的速度是很快的，一夜可以读完厚厚的一本。基本上我采用的是第一遍快速地读，记下大致内容，等到用时就知道这个问题在那本书上谈到过，在拿出来细看。</li>
<li>（建立企业文化的方法之一）……使用漫画家郑辛遥的哲理漫画做辅助，“生活就是这样充满遗憾，当你擦玻璃的时候，脏的东西总是在另一面”，“生气的后果永远比生气的原因严重，擦伤引起的争吵几乎总是以刺伤搞结束”</li>
<li>（企业文化）……不愿意做技术传承的工程师，不能在这个中心工作，这就是我们的一个“天条”。</li>
<li>（企业文化）……团队合作来源于体育界的球队，要点是个人各就各位，分工合作，而不是几个人做同样的事。</li>
<li>（组织架构、职责划分）……我的体会是职责划分越清楚，越利于项目组成员的执行，做事效率也越高。不会出现一件事多人重复做，或者一件事没有人做的情况。有一些公司不愿意在职责划分上花些时间将其定义清楚，而是一味地要员工“主动”，那不是一个好的做法，有时也会造成低效率。“主动”仅应该体现在两人职责的交接处，没发写清楚的细节部分。“做我该做，说我该说”才是一个有序的团队。</li>
<li>师傅领进门，修行在个人——大事是靠培养出来的吗？大画家、大作家、设计大师都是初期得到引导，后期自身修炼的结果。</li>
<li>有测试表明：创造性思维的能力强的人，智商只是中等水平。</li>
<li>一个团队的知识互补是重要的。</li>
<li>对于工程师来说，一个共同的需求就是英文的要求。凡是想做好技术的工程师，英文是必需的，因为大部分深层的技术资料都是英文的。</li>
<li>情商（EQ）是只一个人对情绪的自我认知、自我控制、自我驱策能力以及对他人反馈能力和情绪的识别这5个方面的能力。</li>
<li>（应届毕业生的选择）……“大水出大鱼”，刚毕业的学生要尽可能进大公司。即使你打定注意要自己创业，这也是一条很好的起步之路。知名外企和一流的台资大公司都有相当完善的用人制度、各种管理方法和各种作业流程，做事的观念和方法与学校中收到的教育和主流媒体宣传的也大不相同，对人的评价体系就大不相同。进入这些企业是极好的改变自己的机会，也是给自己一个崭新的视角去看问题。</li>
<li>最重要的就是选择适合你自己的个性、职业发展的公司，选择于你最为重视的价值观相一致的企业，选择植根你内心的人生兴趣相一致的专业。</li>
<li>技术人员书读多了，整天用的是逻辑思维，自然是敏感而多疑，执着甚而固执；想得到别人承认，却又表现得满不在乎；希望碰到知己者，又常感怀才不遇。</li>
<li>有人说，这个世界上人类已经没有共同的理想。其实不然，受过高等教育的研发工程师心中始终埋藏着公平、民主、自由的社会理想，一旦有机会就会表现出来。</li>
<li>我比较推崇的管理方法是职责明晰、流程清楚、方法规范、公平竞争。从管理风格上我喜欢直面事实，不绕弯说出自己的观点，尤其是对技术问题。但这种管理风格对心理脆弱的人效果不好……，所以我会避开这类人。</li>
<li>管理靠细致，对作业面的所有工程师，“心细如发”可能是共同的个性特质要求。……（粗心的表现）……分析下来，也许并不是不负责任，而是心粗。为此，我曾对两位屡教不改的粗心工厂是做过一种培训，就是每天话一小时，让他们吧一碗黑白混合的芝麻分开。……我们还举行用筷子同时夹起三粒生花生米的训练。</li>
<li>建立checklist机制。</li>
<li>在高速运行的企业，最好的报告是“让上司走出电梯前就能看完的报告”。怎样可以做到这样的效果？这就需要反其道而行之，先写结论，在写论证过程，附相关数据表格。</li>
<li>软件行业有一句著名的格言“进来的是垃圾，出去的还是垃圾”。意思是不把工作要求了解清楚，就想当然的做下去，结果一定是产出一堆无用的东西。</li>
<li>新产品研发失败的主要原因有：人不行、钱不够、管理不善、市场不对路。</li>
<li>有没有分析能力是判断一个低阶技术人员和中介技术人员的分水岭。分析能力的强和弱是中高级人才的判断标准之一。</li>
<li>公司前任总经理Steven对流失员工的态度是，他走来走去，还是在这个行业。他到我们的上游企业，我们可能多了一个客户；他到我们的下游企业，以后他会帮我们订货便宜一点；到了我们同行那里，我们多了一个了解信息的渠道；他就是离开这个行业，我们还是可以做朋友。</li>
<li>思维不清晰，不简洁，说话空泛，不能一语中的，这些是中国内地工程师普遍存在的问题，这些缺陷严重地影响了做事的效率。</li>
</ol>
<hr />
<p>如果有读者坚持读到这里了，我在透露一点最有用的道理——一定要亲自去看一下这本书，不然只看我的摘要是没有感觉的，呵呵。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/AnIlNHULbVs" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/11/12/%e8%ae%be%e8%ae%a1%e4%b8%8e%e7%94%9f%e5%ad%98/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/11/12/%e8%ae%be%e8%ae%a1%e4%b8%8e%e7%94%9f%e5%ad%98/</feedburner:origLink></item>
		<item>
		<title>Ubuntu上的包管理：dpkg，apt和aptitude</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/PWoVBfqeIKU/</link>
		<comments>http://www.zhlwish.com/2011/10/23/ubuntu-apt-aptitude-dpkg/#comments</comments>
		<pubDate>Sun, 23 Oct 2011 09:21:40 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[ubuntu]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=823</guid>
		<description><![CDATA[简述 最开始的时候，Linux上的软件以源代码的方式发布，用户下载源代码包（通常打包为.tar.gz），然后自行编译。 dpkg是Debian软件包管理器的基础，它被伊恩·默多克创建于1993年。dpkg与RPM十分相似，同样被用于安装、卸载和供给和.deb软件包相关的信息。 dpkg本身是一个底层的工具，本身并不能从远程包仓库下载包以及处理包的依赖的关系，基于dpkg的上层工具，如APT，则用于从远程获取软件包以及处理复杂的软件包关系。 APT全称Advanced Packaging Tool，可以自动下载，配置，安装二进制或者源代码格式的软件包，因此简化了Unix系统上管理软件的过程。现在Debian和其衍生发行版（如Ubuntu）中都包含了APT。 APT最早是基于dpkg的开发的，只用来处理deb格式的软件包。现在经过APT-RPM组织修改，APT已经可以安装在支持RPM的系统管理RPM包。 而aptitude是一个APT的文本界面客户端，现在也逐渐加入了GUI的界面，详见http://linuxtoy.org/archives/gtk-gui-for-aptitude.html Synaptic是Ubuntu中自带的APT的GUI客户端，也就是传说中的新立得。 dpkg命令 (来自：http://linuxtoy.org/archives/dpkg_reference.html) 命令 作用 dpkg -i package.deb 安装包 dpkg -r package 删除包 dpkg -P package 删除包（包括配置文件） dpkg -L package 列出与该包关联的文件 dpkg -l package 显示该包的版本 dpkg &#8211;unpack package.deb 解开 deb 包的内容 &#8230; <a href="http://www.zhlwish.com/2011/10/23/ubuntu-apt-aptitude-dpkg/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/XRq0lFjvUB767-ZwTJCqv9yZlQY/0/da"><img src="http://feedads.g.doubleclick.net/~a/XRq0lFjvUB767-ZwTJCqv9yZlQY/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/XRq0lFjvUB767-ZwTJCqv9yZlQY/1/da"><img src="http://feedads.g.doubleclick.net/~a/XRq0lFjvUB767-ZwTJCqv9yZlQY/1/di" border="0" ismap="true"></img></a></p><h3><strong>简述</strong></h3>
<p>最开始的时候，Linux上的软件以源代码的方式发布，用户下载源代码包（通常打包为.tar.gz），然后自行编译。</p>
<p>dpkg是Debian软件包管理器的基础，它被伊恩·默多克创建于1993年。dpkg与RPM十分相似，同样被用于安装、卸载和供给和.deb软件包相关的信息。</p>
<p>dpkg本身是一个底层的工具，本身并<strong>不能</strong>从远程包仓库下载包以及处理包的依赖的关系，基于dpkg的上层工具，如APT，则用于<strong>从远程获取</strong>软件包以及<strong>处理复杂的软件包关系</strong>。<br />
<span id="more-823"></span><br />
APT全称Advanced Packaging Tool，可以自动下载，配置，安装二进制或者源代码格式的软件包，因此简化了Unix系统上管理软件的过程。现在Debian和其衍生发行版（如Ubuntu）中都包含了APT。</p>
<p>APT最早是基于dpkg的开发的，只用来处理deb格式的软件包。现在经过APT-RPM组织修改，APT已经可以安装在支持RPM的系统管理RPM包。</p>
<p>而aptitude是一个APT的文本界面客户端，现在也逐渐加入了GUI的界面，详见<a title="Aptitude 有了 GTK+ GUI" href="http://linuxtoy.org/archives/gtk-gui-for-aptitude.html" target="_blank">http://linuxtoy.org/archives/gtk-gui-for-aptitude.html</a></p>
<p>Synaptic是Ubuntu中自带的APT的GUI客户端，也就是传说中的新立得。</p>
<h3><strong>dpkg命令</strong></h3>
<p>(来自：<a href="http://linuxtoy.org/archives/dpkg_reference.html" target="_blank">http://linuxtoy.org/archives/dpkg_reference.html</a>)</p>
<table>
<tbody>
<tr>
<th width="200">命令</th>
<th>作用</th>
</tr>
<tr>
<td>dpkg -i package.deb</td>
<td>安装包</td>
</tr>
<tr>
<td>dpkg -r package</td>
<td>删除包</td>
</tr>
<tr>
<td>dpkg -P package</td>
<td>删除包（包括配置文件）</td>
</tr>
<tr>
<td>dpkg -L package</td>
<td>列出与该包关联的文件</td>
</tr>
<tr>
<td>dpkg -l package</td>
<td>显示该包的版本</td>
</tr>
<tr>
<td>dpkg &#8211;unpack package.deb</td>
<td>解开 deb 包的内容</td>
</tr>
<tr>
<td>dpkg -S keyword</td>
<td>搜索所属的包内容</td>
</tr>
<tr>
<td><span style="color: #e500ff;">dpkg -l</span></td>
<td><span style="color: #e500ff;">列出当前已安装的包</span></td>
</tr>
<tr>
<td>dpkg -c package.deb</td>
<td>列出 deb 包的内容</td>
</tr>
<tr>
<td>dpkg &#8211;configure package</td>
<td>配置包</td>
</tr>
</tbody>
</table>
<p>注意：更多选项可通过 dpkg -h 查询，有些指令需要超级用户权限才能执行</p>
<h3><strong>APT命令</strong></h3>
<p>(来自：<a href="http://linuxtoy.org/archives/apt_reference.html" target="_blank">http://linuxtoy.org/archives/apt_reference.html</a>)</p>
<table>
<tbody>
<tr>
<th width="200">命令</th>
<th>作用</th>
</tr>
<tr>
<td>apt-cache search package</td>
<td>搜索包</td>
</tr>
<tr>
<td>apt-cache show package</td>
<td>获取包的相关信息，如说明、大小、版本等</td>
</tr>
<tr>
<td>sudo apt-get install package</td>
<td>安装包</td>
</tr>
<tr>
<td>sudo apt-get install package &#8211;reinstall</td>
<td>重新安装包</td>
</tr>
<tr>
<td>sudo apt-get -f install</td>
<td>强制安装</td>
</tr>
<tr>
<td>sudo apt-get remove package</td>
<td>删除包</td>
</tr>
<tr>
<td>sudo apt-get remove package <span style="color: #ba00ff;">&#8211;purge</span></td>
<td>删除包，包括删除配置文件等</td>
</tr>
<tr>
<td>sudo apt-get autoremove</td>
<td>自动删除不需要的包</td>
</tr>
<tr>
<td>sudo apt-get update</td>
<td>更新源</td>
</tr>
<tr>
<td>sudo apt-get upgrade</td>
<td>更新已安装的包</td>
</tr>
<tr>
<td>sudo apt-get dist-upgrade</td>
<td>升级系统</td>
</tr>
<tr>
<td>sudo apt-get dselect-upgrade</td>
<td>使用 dselect 升级</td>
</tr>
<tr>
<td>apt-cache depends package</td>
<td>了解使用依赖</td>
</tr>
<tr>
<td>apt-cache rdepends package</td>
<td>了解某个具体的依赖</td>
</tr>
<tr>
<td>sudo apt-get <span style="color: #ba00ff;">build-dep</span> package</td>
<td>安装相关的编译环境</td>
</tr>
<tr>
<td>apt-get source package</td>
<td>下载该包的源代码</td>
</tr>
<tr>
<td>sudo apt-get clean &amp;&amp; sudo apt-get autoclean</td>
<td>清理下载文件的存档</td>
</tr>
<tr>
<td>sudo apt-get check</td>
<td>检查是否有损坏的依赖</td>
</tr>
</tbody>
</table>
<p>备注：package 为软件包名称。</p>
<h3><strong>aptitude命令</strong></h3>
<p>（来自<a href="http://linuxtoy.org/archives/aptitude_quick_reference.html" target="_blank">http://linuxtoy.org/archives/aptitude_quick_reference.html</a>）<br />
aptitude是基于APT的又一个包管理的前端，aptitude似乎在处理依赖问题上更佳一些。据说aptitude 另外用一份数据量很小的扩展标记来实现所谓更佳的管理，我没有发现有什么比apt命令更加牛逼的功能，不过看起来命令比apt要简洁。</p>
<table>
<tbody>
<tr>
<th width="200">命令</th>
<th>作用</th>
</tr>
<tr>
<td>aptitude update</td>
<td>更新可用的包列表</td>
</tr>
<tr>
<td>aptitude upgrade</td>
<td>升级可用的包</td>
</tr>
<tr>
<td>aptitude dist-upgrade</td>
<td>将系统升级到新的发行版</td>
</tr>
<tr>
<td>aptitude install pkgname</td>
<td>安装包</td>
</tr>
<tr>
<td>aptitude remove pkgname</td>
<td>删除包</td>
</tr>
<tr>
<td>aptitude purge pkgname</td>
<td>删除包及其配置文件</td>
</tr>
<tr>
<td>aptitude search string</td>
<td>搜索包</td>
</tr>
<tr>
<td>aptitude show pkgname</td>
<td>显示包的详细信息</td>
</tr>
<tr>
<td>aptitude clean</td>
<td>删除下载的包文件</td>
</tr>
<tr>
<td>aptitude autoclean</td>
<td>仅删除过期的包文件</td>
</tr>
</tbody>
</table>
<p>当然aptitude也是text-based，也就是命令行模式的</p>
<h3><strong>Synaptic</strong></h3>
<p>由于synaptic是GUI界面的，没啥命令好说的，其实这个在Ubuntu里面也挺少用到的，更多的还是通过apt-get命令就可以搞定。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/PWoVBfqeIKU" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/10/23/ubuntu-apt-aptitude-dpkg/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/10/23/ubuntu-apt-aptitude-dpkg/</feedburner:origLink></item>
		<item>
		<title>XMPP中资源/Resource的解释和JID</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/7cJKKmlxkOY/</link>
		<comments>http://www.zhlwish.com/2011/09/23/xmpp_resource_jid/#comments</comments>
		<pubDate>Fri, 23 Sep 2011 08:31:20 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Python]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=816</guid>
		<description><![CDATA[因为之前写过《使用PyXMPP向GTalk发送消息》一文，最近被一个研究XMPP协议的学妹问到XMPP协议中的资源（Resource）的意思。其实我开始也是一知半解，而且学妹挺诚心的样子，就仔细看了看XMPP协议的文档，这里也感谢这位学妹提供的XMPP协议（RFC3920）的中文版和英文版，其实我以前写用pyxmpp的时候也没有仔细看XMPP协议的。 不看不知道，一看吓一跳，原来所谓的Resource和我一直很欣赏的Google Talk的多客户端同时在线的功能有关系，Google Talk就是基于XMPP协议的。 首先举几个JID的例子，比如下面几个都是完整的JID: xxx@gmail.com /gtalk-client xxx@gmail.com /plus.google.com xxx@gmail.com /gmail xxx@gmail.com /sony-errision-x10-android JID实际上是3部分组成的：节点名（上面四个JID中的“xxx”），域名（上面四个JID中的“gmail.com”，一般是主服务器的域名），资源名（上面四个JID中最后面不同的那部分） 这四个JID都对应到某人的google帐号（xxx@gmail.com），只不过一个对应windows gtalk客户端，第二个对应google plus网页的上的那个聊天窗口，第三个对应google talk的网页窗口，第四个对应手机上的google talk。注意这里资源的名字只是我自己瞎想出来的，可能一般实现的时候会直接有服务器生成一个随机字符串吧。 和QQ不一样的是，XMPP允许一个帐号在不同的地方登录，比如我的电脑、google plus网页、gmail、手机上的google talk现在都是登录状态，别人给我发送消息的时候，我的四个client都会提示我有收到新的消息，但是当我选择用手机回复的时候，本次会话（session）所有消息都会只发送到我的手机，而其他的client（如windows上的google client、gmail里面的client）就不会再收到消息了。 因此除了帐号(xxx@gmail.com)以外，会有另外一个标识符来标识我使用的这种client，这个client就是上文提到的resource，这里上面4个帐号中，email地址后面的字符串就是resource id了 因此为了确认你使用的哪一个客户端，需要resource绑定。绑定后的JID才是一个完整的JID。 上面就是我对XMPP中Resource的理解，也特别感谢这位学妹的问题，才让我对XMPP有了更深入了解的机会。]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/A5H4gvsZSVR-O77shaee5failrA/0/da"><img src="http://feedads.g.doubleclick.net/~a/A5H4gvsZSVR-O77shaee5failrA/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/A5H4gvsZSVR-O77shaee5failrA/1/da"><img src="http://feedads.g.doubleclick.net/~a/A5H4gvsZSVR-O77shaee5failrA/1/di" border="0" ismap="true"></img></a></p><p>因为之前写过<a href="http://www.zhlwish.com/2011/04/04/pyxmpp_gtalk/" title="使用PyXMPP向GTalk发送消息">《使用PyXMPP向GTalk发送消息》</a>一文，最近被一个研究XMPP协议的学妹问到XMPP协议中的资源（Resource）的意思。其实我开始也是一知半解，而且学妹挺诚心的样子，就仔细看了看XMPP协议的文档，这里也感谢这位学妹提供的XMPP协议（RFC3920）的<a href="http://zhlwish.googlecode.com/files/RFC3920%E4%B8%AD%E6%96%87%E7%BF%BB%E8%AF%91%E7%89%88.doc" target="_blank">中文版</a>和<a href="http://zhlwish.googlecode.com/files/rfc3920.pdf" target="_blank">英文版</a>，其实我以前写用pyxmpp的时候也没有仔细看XMPP协议的。</p>
<p>不看不知道，一看吓一跳，原来所谓的Resource和我一直很欣赏的Google Talk的多客户端同时在线的功能有关系，Google Talk就是基于XMPP协议的。<br />
<span id="more-816"></span><br />
首先举几个JID的例子，比如下面几个都是完整的JID:</p>
<pre>
xxx@gmail.com /gtalk-client
xxx@gmail.com /plus.google.com
xxx@gmail.com /gmail
xxx@gmail.com /sony-errision-x10-android
</pre>
<p>JID实际上是3部分组成的：节点名（上面四个JID中的“xxx”），域名（上面四个JID中的“gmail.com”，一般是主服务器的域名），资源名（上面四个JID中最后面不同的那部分）</p>
<p>这四个JID都对应到某人的google帐号（xxx@gmail.com），只不过一个对应windows gtalk客户端，第二个对应google plus网页的上的那个聊天窗口，第三个对应google talk的网页窗口，第四个对应手机上的google talk。注意这里资源的名字只是我自己瞎想出来的，可能一般实现的时候会直接有服务器生成一个随机字符串吧。</p>
<p>和QQ不一样的是，XMPP允许一个帐号在不同的地方登录，比如我的电脑、google plus网页、gmail、手机上的google talk现在都是登录状态，别人给我发送消息的时候，我的四个client都会提示我有收到新的消息，但是当我选择用手机回复的时候，本次会话（session）所有消息都会只发送到我的手机，而其他的client（如windows上的google client、gmail里面的client）就不会再收到消息了。</p>
<p>因此除了帐号(xxx@gmail.com)以外，会有另外一个标识符来标识我使用的这种client，这个client就是上文提到的resource，这里上面4个帐号中，email地址后面的字符串就是resource id了</p>
<p>因此为了确认你使用的哪一个客户端，需要resource绑定。绑定后的JID才是一个完整的JID。</p>
<p>上面就是我对XMPP中Resource的理解，也特别感谢这位学妹的问题，才让我对XMPP有了更深入了解的机会。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/7cJKKmlxkOY" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/09/23/xmpp_resource_jid/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/09/23/xmpp_resource_jid/</feedburner:origLink></item>
		<item>
		<title>相信未来</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/QFMgcTZ_-0c/</link>
		<comments>http://www.zhlwish.com/2011/09/20/believe-future/#comments</comments>
		<pubDate>Mon, 19 Sep 2011 17:06:11 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>
		<category><![CDATA[相信未来]]></category>
		<category><![CDATA[诗]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=796</guid>
		<description><![CDATA[当蜘蛛网无情地查封了我的炉台 当灰烬的余烟叹息着贫困的悲哀 我依然固执地铺平失望的灰烬 用美丽的雪花写下：相信未来 当我的紫葡萄化为深秋的露水 当我的鲜花依偎在别人的情怀 我依然固执地用凝霜的枯藤 在凄凉的大地上写下：相信未来 我要用手指那涌向天边的排浪 我要用手掌那托住太阳的大海 摇曳着曙光那枝温暖漂亮的笔杆 用孩子的笔体写下：相信未来 我之所以坚定地相信未来 是我相信未来人们的眼睛 她有拨开历史风尘的睫毛 她有看透岁月篇章的瞳孔 不管人们对于我们腐烂的皮肉 那些迷途的惆怅、失败的苦痛 是寄予感动的热泪、深切的同情 还是给以轻蔑的微笑、辛辣的嘲讽 我坚信人们对于我们的脊骨 那无数次的探索、迷途、失败和成功 一定会给予热情、客观、公正的评定 是的，我焦急地等待着他们的评定 朋友，坚定地相信未来吧 相信不屈不挠的努力 相信战胜死亡的年轻 相信未来、热爱生命 食指/1968年/北京 今晚意外的聆听了新东方俞敏洪老师的演讲《相信未来》，结束的时候，俞老师背诵了这首《相信未来》。听到这首倍感熟悉的诗，我突然记起高中的时候我曾经疯狂的迷恋这首诗，甚至比《山高路远》（没有比人更高的山/没有比脚更长的路）一样。 突然记起，我已经好久，没相信未来。 我曾经很乐观，认为我可以搞定一切，但是随着年龄的增长，逐渐认识到自己的力量永远是一颗小水珠，只能在初夏早晨的那一刹那，彩虹洋溢。慢慢的开始认命。 中考那年，妈找了个瞎眼算命先生给我算命，当时深受受马克思辩证唯物主义毒害，于是当着算命先生的面发了句牢骚，说“算命都是见鬼的”，方言“见鬼”表示深深的轻蔑和不屑。算命先生没责怪我的意思，不过我也没拗过妈，抽了个签。算出来的具体是什么命我记不得，我妈估计记得，只隐约记得是长大了要做大官。我则再次表达了不屑。 算命先生走后，妈教育我，即使不信命，也不能说那样的话，至少要对算命先生表示尊重。这么多年以来，每当在天桥上、地下通道口看到乞讨的老人，我总想起这句话。 十年后，在校外办完事情匆忙走在大城市武汉的街头，不经意瞥到路边摆摊算命的算命先生，眼睛不瞎的那种。突然心头一动，有种冲动想算一下命，虽然在心中仍然觉得算命实在是件荒唐的事儿。可是，就是有那么一股子冲动，现在依然有。 又过了几年的一个五一节，妈来武汉玩儿几天。妈那个时代的农村妇女对黄鹤楼都有一种莫名的情节，他们经常对我说的是“湖北有个黄鹤楼,半截伸在天里头”。反而在武汉生活了8年多的我没有任何感觉，带妈爬上了黄鹤楼，她很高兴，拍了不少照片。我心想，有点想头真好。 当然不得不去归元寺，我外婆是虔诚的佛教徒，我外公患上肝癌的时候开始信的，直到现在外公都已经去世十四年，她还供奉着观音娘娘。大名鼎鼎的归元寺自然也得带我妈去看看。到了罗汉堂，有求签，解签。我好像也虔诚了，听从了妈，花了二十块钱解签，具体什么内容现在恐怕也得问她了。我印象最深的是，高僧解签是要花更多的钱的，这无疑让我对佛曰“众生平等”的印象大打折扣，看起来佛也喜欢的是有钱人。 直到今天，突然有听到这首诗，突然醒悟，命运原来不在算命先生嘴巴里，也不在佛祖的签上，却是在你我的意识里，深深的潜藏。该信未来。]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/by8Sws0zYBsvQ6YGHM7FwtobD4s/0/da"><img src="http://feedads.g.doubleclick.net/~a/by8Sws0zYBsvQ6YGHM7FwtobD4s/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/by8Sws0zYBsvQ6YGHM7FwtobD4s/1/da"><img src="http://feedads.g.doubleclick.net/~a/by8Sws0zYBsvQ6YGHM7FwtobD4s/1/di" border="0" ismap="true"></img></a></p><div style="margin: auto; text-align: left; width: 220px;">当蜘蛛网无情地查封了我的炉台<br />
当灰烬的余烟叹息着贫困的悲哀<br />
我依然固执地铺平失望的灰烬<br />
用美丽的雪花写下：相信未来<br />
<span id="more-796"></span><br />
当我的紫葡萄化为深秋的露水<br />
当我的鲜花依偎在别人的情怀<br />
我依然固执地用凝霜的枯藤<br />
在凄凉的大地上写下：相信未来</p>
<p>我要用手指那涌向天边的排浪<br />
我要用手掌那托住太阳的大海<br />
摇曳着曙光那枝温暖漂亮的笔杆<br />
用孩子的笔体写下：相信未来</p>
<p>我之所以坚定地相信未来<br />
是我相信未来人们的眼睛<br />
她有拨开历史风尘的睫毛<br />
她有看透岁月篇章的瞳孔</p>
<p>不管人们对于我们腐烂的皮肉<br />
那些迷途的惆怅、失败的苦痛<br />
是寄予感动的热泪、深切的同情<br />
还是给以轻蔑的微笑、辛辣的嘲讽</p>
<p>我坚信人们对于我们的脊骨<br />
那无数次的探索、迷途、失败和成功<br />
一定会给予热情、客观、公正的评定<br />
是的，我焦急地等待着他们的评定</p>
<p>朋友，坚定地相信未来吧<br />
相信不屈不挠的努力<br />
相信战胜死亡的年轻<br />
相信未来、热爱生命
</p></div>
<div style="text-align: right; width: 400px;">食指/1968年/北京</div>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/09/believe_future.jpg" rel="lightbox[796]"><img class="aligncenter size-medium wp-image-797" title="相信未来" src="http://www.zhlwish.com/wp-content/uploads/2011/09/believe_future-300x217.jpg" alt="" width="300" height="217" /></a></p>
<p>今晚意外的聆听了新东方俞敏洪老师的演讲《相信未来》，结束的时候，俞老师背诵了这首《相信未来》。听到这首倍感熟悉的诗，我突然记起高中的时候我曾经疯狂的迷恋这首诗，甚至比《山高路远》（没有比人更高的山/没有比脚更长的路）一样。</p>
<p>突然记起，我已经好久，没相信未来。</p>
<p>我曾经很乐观，认为我可以搞定一切，但是随着年龄的增长，逐渐认识到自己的力量永远是一颗小水珠，只能在初夏早晨的那一刹那，彩虹洋溢。慢慢的开始认命。</p>
<p>中考那年，妈找了个瞎眼算命先生给我算命，当时深受受马克思辩证唯物主义毒害，于是当着算命先生的面发了句牢骚，说“算命都是见鬼的”，方言“见鬼”表示深深的轻蔑和不屑。算命先生没责怪我的意思，不过我也没拗过妈，抽了个签。算出来的具体是什么命我记不得，我妈估计记得，只隐约记得是长大了要做大官。我则再次表达了不屑。</p>
<p>算命先生走后，妈教育我，即使不信命，也不能说那样的话，至少要对算命先生表示尊重。这么多年以来，每当在天桥上、地下通道口看到乞讨的老人，我总想起这句话。</p>
<p>十年后，在校外办完事情匆忙走在大城市武汉的街头，不经意瞥到路边摆摊算命的算命先生，眼睛不瞎的那种。突然心头一动，有种冲动想算一下命，虽然在心中仍然觉得算命实在是件荒唐的事儿。可是，就是有那么一股子冲动，现在依然有。</p>
<p>又过了几年的一个五一节，妈来武汉玩儿几天。妈那个时代的农村妇女对黄鹤楼都有一种莫名的情节，他们经常对我说的是“湖北有个黄鹤楼,半截伸在天里头”。反而在武汉生活了8年多的我没有任何感觉，带妈爬上了黄鹤楼，她很高兴，拍了不少照片。我心想，有点想头真好。</p>
<p>当然不得不去归元寺，我外婆是虔诚的佛教徒，我外公患上肝癌的时候开始信的，直到现在外公都已经去世十四年，她还供奉着观音娘娘。大名鼎鼎的归元寺自然也得带我妈去看看。到了罗汉堂，有求签，解签。我好像也虔诚了，听从了妈，花了二十块钱解签，具体什么内容现在恐怕也得问她了。我印象最深的是，高僧解签是要花更多的钱的，这无疑让我对佛曰“众生平等”的印象大打折扣，看起来佛也喜欢的是有钱人。</p>
<p>直到今天，突然有听到这首诗，突然醒悟，命运原来不在算命先生嘴巴里，也不在佛祖的签上，却是在你我的意识里，深深的潜藏。该信未来。</p>
<p style="text-align:center"><object width="480" height="400"><param name="movie" value="http://player.youku.com/player.php/sid/XMTUxNzIwMTAw/v.swf"></param><param name="allowFullScreen" value="true"></param><param name="allowscriptaccess" value="never"></param><param name="allownetworking" value="internal"></param><param name="flashvars" value="isShowRelatedVideo=false&showAd=0&show_pre=1&show_next=1&isAutoPlay=false&isDebug=false&UserID=&winType=interior&playMovie=true&MMControl=false&MMout=false&RecordCode=1001,1002,1003,1004,1005,1006,2001,3001,3002,3003,3004,3005,3007,3008,9999" /><embed src="http://player.youku.com/player.php/sid/XMTUxNzIwMTAw/v.swf" type="application/x-shockwave-flash" allowscriptaccess="never" allownetworking="internal" allowfullscreen="true" width="480" height="400" flashvars="isShowRelatedVideo=false&showAd=0&show_pre=1&show_next=1&isAutoPlay=false&isDebug=false&UserID=&winType=interior&playMovie=true&MMControl=false&MMout=false&RecordCode=1001,1002,1003,1004,1005,1006,2001,3001,3002,3003,3004,3005,3007,3008,9999"></embed></object></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/QFMgcTZ_-0c" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/09/20/believe-future/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/09/20/believe-future/</feedburner:origLink></item>
		<item>
		<title>Eclipse JFace Binding/绑定 (3)</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/vmLgXVaG16M/</link>
		<comments>http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-3/#comments</comments>
		<pubDate>Sat, 17 Sep 2011 14:28:19 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Eclispe RCP]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=786</guid>
		<description><![CDATA[前文Eclipse JFace Binding/绑定 (1)”和Eclipse JFace Binding/绑定 (2)”分别讲述了JavaBean API的事件机制和Eclipse JFace Binding的SWT控件属性和JavaBean属性的绑定。本文是本系列的最后一篇，讲述JFace中TableViewer、TreeViewer和ListViewer的绑定，由于TableViewer比较有代表性，因此使用TableViewer作为示例。 为什么需要WritableList、WritableSet和WritableMap 在做任何事情之前，先要提出一个为什么，“当你保持一颗好奇的心，当你愿意去问“为什么”，而不是一味得不假思索得接受，你便能够从一件事物的不同角度去审度，你就站得更高，看得更远”——这是 《Sandra Lee: 人生很短，做自己喜欢的事 》中的一句话，我很喜欢。 提出这个问题，潜台词肯定是为什么不能直接用List、Set、Map呢？原因在于集合对象不同于普通对象，集合对象包括了一组对象，这组对象本身的属性改变需要监听自然不必说，对象的添加、删除也是需要监听的，因此Java Collection API中的List、Set和Map就不够用了，更何况几何对象中所包括的那一组对象还必须封装到一个WritableValue对象中，不然元素和GUI的绑定又得失效了。 那么这么多复杂的工作就让WritableList去干吧。 JavaBean中的List属性 我们先模拟一下有钱人，他们都能买几套房子，因此都有几个地址，将地址列表作为有钱人的一个属性。 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 &#8230; <a href="http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-3/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/CMnNhBa6uTYE2mj4izqO_-lunbo/0/da"><img src="http://feedads.g.doubleclick.net/~a/CMnNhBa6uTYE2mj4izqO_-lunbo/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/CMnNhBa6uTYE2mj4izqO_-lunbo/1/da"><img src="http://feedads.g.doubleclick.net/~a/CMnNhBa6uTYE2mj4izqO_-lunbo/1/di" border="0" ismap="true"></img></a></p><p>前文<a href="http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-1/" title="Eclipse JFace Binding/绑定 (1)">Eclipse JFace Binding/绑定 (1)”</a>和<a href="http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-2/" title="Eclipse JFace Binding/绑定 (2)">Eclipse JFace Binding/绑定 (2)”</a>分别讲述了JavaBean API的事件机制和Eclipse JFace Binding的SWT控件属性和JavaBean属性的绑定。本文是本系列的最后一篇，讲述JFace中TableViewer、TreeViewer和ListViewer的绑定，由于TableViewer比较有代表性，因此使用TableViewer作为示例。</p>
<p><strong>为什么需要WritableList、WritableSet和WritableMap</strong></p>
<p>在做任何事情之前，先要提出一个为什么，“当你保持一颗好奇的心，当你愿意去问“为什么”，而不是一味得不假思索得接受，你便能够从一件事物的不同角度去审度，你就站得更高，看得更远”——这是 <a href="http://www.china30s.com/?p=1385" target="_blank">《Sandra Lee: 人生很短，做自己喜欢的事 》</a>中的一句话，我很喜欢。</p>
<p>提出这个问题，潜台词肯定是为什么不能直接用List、Set、Map呢？原因在于集合对象不同于普通对象，集合对象包括了一组对象，这组对象本身的属性改变需要监听自然不必说，对象的添加、删除也是需要监听的，因此Java Collection API中的List、Set和Map就不够用了，更何况几何对象中所包括的那一组对象还必须封装到一个WritableValue对象中，不然元素和GUI的绑定又得失效了。<br />
<span id="more-786"></span><br />
那么这么多复杂的工作就让WritableList去干吧。</p>
<p><strong>JavaBean中的List属性</strong></p>
<p>我们先模拟一下有钱人，他们都能买几套房子，因此都有几个地址，将地址列表作为有钱人的一个属性。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.jfacebinding.model</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.beans.PropertyChangeSupport</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.util.ArrayList</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.util.List</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> RichPerson <span style="color: #000000; font-weight: bold;">extends</span> <span style="color: #003399;">PropertyChangeSupport</span> <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> RichPerson<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span><span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">null</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> RichPerson<span style="color: #009900;">&#40;</span><span style="color: #003399;">Object</span> sourceBean<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">super</span><span style="color: #009900;">&#40;</span>sourceBean<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">String</span> name<span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">private</span> List<span style="color: #339933;">&lt;</span>address<span style="color: #339933;">&gt;</span> addresses<span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">String</span> getName<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> name<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setName<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> name<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">firePropertyChange</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;name&quot;</span>, <span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">name</span>, <span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">name</span> <span style="color: #339933;">=</span> name<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> List<span style="color: #339933;">&lt;/</span>address<span style="color: #339933;">&gt;&lt;</span>address<span style="color: #339933;">&gt;</span> getAddresses<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>addresses <span style="color: #339933;">==</span> <span style="color: #000066; font-weight: bold;">null</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
			addresses <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ArrayList<span style="color: #339933;">&lt;/</span>address<span style="color: #339933;">&gt;&lt;</span>address<span style="color: #339933;">&gt;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
		<span style="color: #000000; font-weight: bold;">return</span> addresses<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setAddresses<span style="color: #009900;">&#40;</span>List<span style="color: #339933;">&lt;/</span>address<span style="color: #339933;">&gt;&lt;</span>address<span style="color: #339933;">&gt;</span> addresses<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">firePropertyChange</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;addresses&quot;</span>, <span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">addresses</span>,
				<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">addresses</span> <span style="color: #339933;">=</span> addresses<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000000; font-weight: bold;">class</span> Address <span style="color: #000000; font-weight: bold;">extends</span> <span style="color: #003399;">PropertyChangeSupport</span> <span style="color: #009900;">&#123;</span>
&nbsp;
		<span style="color: #000000; font-weight: bold;">public</span> Address<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">this</span><span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">null</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
&nbsp;
		<span style="color: #000000; font-weight: bold;">public</span> Address<span style="color: #009900;">&#40;</span><span style="color: #003399;">Object</span> sourceBean<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">super</span><span style="color: #009900;">&#40;</span>sourceBean<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
&nbsp;
		<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">String</span> street<span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">String</span> city<span style="color: #339933;">;</span>
&nbsp;
		<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">String</span> getStreet<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">return</span> street<span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
&nbsp;
		<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setStreet<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> street<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">firePropertyChange</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;street&quot;</span>, <span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">street</span>, <span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">street</span> <span style="color: #339933;">=</span> street<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
&nbsp;
		<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">String</span> getCity<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">return</span> city<span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
&nbsp;
		<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setCity<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> city<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">firePropertyChange</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;city&quot;</span>, <span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">city</span>, <span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">city</span> <span style="color: #339933;">=</span> city<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span>
<span style="color: #339933;">&lt;/</span>address<span style="color: #339933;">&gt;</span></pre></td></tr></table></div>

<p><strong>将List绑定到TableView上</strong></p>
<p>下面的目标是将List绑定到TableView上，首先我们不管RichPerson这个master，先对付一个Address的列表绑定。下面代码先创建了一个addresses列表。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #003399;">ArrayList</span> addresses <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ArrayList<span style="color: #339933;">&lt;</span>address<span style="color: #339933;">&gt;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
Address address <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Address<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #666666; font-style: italic;">//暴露了，暴露了</span>
address.<span style="color: #006633;">setCity</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;武汉&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
address.<span style="color: #006633;">setStreet</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;珞喻路&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
addresses.<span style="color: #006633;">add</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> Address<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
DataBindingContext bindingContext <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> DataBindingContext<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #666666; font-style: italic;">//设置ContentProvider</span>
ObservableListContentProvider listContentProvider <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ObservableListContentProvider<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
tableViewer.<span style="color: #006633;">setContentProvider</span><span style="color: #009900;">&#40;</span>listContentProvider<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #666666; font-style: italic;">//设置LabelProvider</span>
IObservableMap<span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> observeMaps <span style="color: #339933;">=</span> BeansObservables.<span style="color: #006633;">observeMaps</span><span style="color: #009900;">&#40;</span>
				listContentProvider.<span style="color: #006633;">getKnownElements</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>, 
				Address.<span style="color: #000000; font-weight: bold;">class</span>, <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">String</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#123;</span><span style="color: #0000ff;">&quot;city&quot;</span>, <span style="color: #0000ff;">&quot;street&quot;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
tableViewer.<span style="color: #006633;">setLabelProvider</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> ObservableMapLabelProvider<span style="color: #009900;">&#40;</span>observeMaps<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #666666; font-style: italic;">//设置Input</span>
WritableList writableList <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> WritableList<span style="color: #009900;">&#40;</span>addresses, Person.<span style="color: #000000; font-weight: bold;">class</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
tableViewer.<span style="color: #006633;">setInput</span><span style="color: #009900;">&#40;</span>writableList<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #339933;">&lt;/</span>address<span style="color: #339933;">&gt;</span></pre></td></tr></table></div>

<p>好啦，这样就完了，我们在TableView中去添加，删除会直接绑定到addresses列表上。其实看起来和TableView显示普通List也没有什么区别，老三样：设置ContentProvider、设置LabelProvider、<br />
设置Input，只不过这里升级了，不再是ArrayContentProvider，也不是LabelProvider而是ObservableListContentProvider和ObservableMapLabelProvider了。</p>
<p><strong>将RichPerson对象中的addresses属性绑定到TableView</strong></p>
<p>严格意义上来讲不是将RichPerson对象的属性绑定到底TableView，而是将RichPerson对象的代理WritableValue的addresses属性绑定到TableView。因为如果只是RichPerson对象，那么就和前面的没有什么区别了，创建WritableList的时候直接像下面这样写就完了：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;">WritableList writableList <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> WritableList<span style="color: #009900;">&#40;</span>richPerson.<span style="color: #006633;">getAddresses</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>, RichPerson.<span style="color: #000000; font-weight: bold;">class</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></td></tr></table></div>

<p>为了尝试一点不同，我们先创建一个封装了richPerson的WritableValue对象，如下：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;">RichPerson richPerson <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> RichPerson<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
WritableValue model <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> WritableValue<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
model.<span style="color: #006633;">setValue</span><span style="color: #009900;">&#40;</span>richPerson<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></td></tr></table></div>

<p>好吧，终于快结束了，这里隆重推出在<a href="http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-2/" title="Eclipse JFace Binding/绑定 (2)">Eclipse JFace Binding/绑定 (2)”</a>中已经提到，但是没有说明的observeDetailList()方法，此方法有三个参数:</p>
<ol>
<li>第一个是master对象，这里就是我们在上面代码中创建的model</li>
<li>第二个是属性名称，这里我们要绑定RichPerson对象的addresses属性</li>
<li>第三个是属性的元素类型，这里我们要绑定的是Address类型</li>
</ol>
<p>因此，绑定的代码如下，前面的设置ContentProvider和设置LabelProvider是一样的，最后的两句话修改如下。这里需要注意的是writableList变成了IObservableList类型，因为WritableList继承自IObservableList，而且observeDetailList返回值也是IObservableList，我没有尝试去做强制类型转化，当然，你可以试一下。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #666666; font-style: italic;">//设置Input</span>
IObservableList writableList <span style="color: #339933;">=</span> BeansObservables.<span style="color: #006633;">observeDetailList</span><span style="color: #009900;">&#40;</span>model, <span style="color: #0000ff;">&quot;addresses&quot;</span>, Address.<span style="color: #000000; font-weight: bold;">class</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
tableViewer.<span style="color: #006633;">setInput</span><span style="color: #009900;">&#40;</span>writableList<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></td></tr></table></div>

<p><strong>小结</strong><br />
写了一天，终于写完了，之所以一定要写下来，因为Eclipse JFace的Binding机制的确给我这样的懒程序猿带来了很大的好处，而且在Eclipse的代码里面学到了很多设计模式的作用，如策略模式、观察哲模式、装饰器模式、简单工厂模式。另外，由于我能找到的材料都是英文的，中文基本没有，有也是翻译的英文，而且以示例为主，没有总结和分析，因此就下决心要写下来。等我有空了，在翻译成英文的样子，发布出去。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/vmLgXVaG16M" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-3/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-3/</feedburner:origLink></item>
		<item>
		<title>Eclipse JFace Binding/绑定 (2)</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/oC_HMCcgOHo/</link>
		<comments>http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-2/#comments</comments>
		<pubDate>Sat, 17 Sep 2011 13:15:11 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Eclispe RCP]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=775</guid>
		<description><![CDATA[前文《Eclipse JFace Binding/绑定 (1)》介绍了JavaBean的事件机制，Eclipse的绑定利用了这种机制，（据说Eclipse Binding的下一个目标是Pojo对象的双向绑定，利用asm这样的字节码操作库）。 绑定针对对象实例而不是类型 在深入之前，需要明确的是，在Java中绑定永远是针对对象实例的绑定，而不是针对对象类型的绑定。也就是说下面的代码会使model之前注册的监听器失效。 Model model = new Model&#40;&#41;; model.addPropertyChangeListener&#40;new IPropertyChangeListener&#40;&#41;&#123; public void propertyChangeListener&#40;PropertyChangeEvent evt&#41;&#123; System.out.println&#40;evt.getPropertyName&#40;&#41; + “ changed”&#41;; &#125; &#125;&#41;; model = new Model&#40;&#41;; IObservable接口 Eclipse绑定的核心是IObservableValue、IObservableList，通过实现这些接口对GUI和模型进行监听，我把实现了这些接口的对象成为绑定对象。包括： IObservable &#8211; 所有Observable接口的根接口，提供了对对象实例变化的监听机制 IObservableValue &#8211; 提供了getValue()和setValue()方法，提供了监听value改变的机制 IVetoableValue &#8211; 继承自IObservableValue，提供了在value变化之前进行事件处理的机制 IObservableCollection &#8230; <a href="http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-2/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/FYqD9G0HfUgWWOSdvJ0l-anWCcU/0/da"><img src="http://feedads.g.doubleclick.net/~a/FYqD9G0HfUgWWOSdvJ0l-anWCcU/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/FYqD9G0HfUgWWOSdvJ0l-anWCcU/1/da"><img src="http://feedads.g.doubleclick.net/~a/FYqD9G0HfUgWWOSdvJ0l-anWCcU/1/di" border="0" ismap="true"></img></a></p><p>前文<a href="http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-1/" title="Eclipse JFace Binding/绑定 (1)" target="_blank">《Eclipse JFace Binding/绑定 (1)》</a>介绍了JavaBean的事件机制，Eclipse的绑定利用了这种机制，（据说Eclipse Binding的下一个目标是Pojo对象的双向绑定，利用<a href="http://asm.ow2.org/" title="Java asm" target="_blank">asm</a>这样的字节码操作库）。</p>
<p><strong>绑定针对对象实例而不是类型</strong></p>
<p>在深入之前，需要明确的是，在Java中绑定永远是针对对象实例的绑定，而不是针对对象类型的绑定。也就是说下面的代码会使model之前注册的监听器失效。<span id="more-775"></span></p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">Model model <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Model<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
model.<span style="color: #006633;">addPropertyChangeListener</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> IPropertyChangeListener<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> propertyChangeListener<span style="color: #009900;">&#40;</span><span style="color: #003399;">PropertyChangeEvent</span> evt<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		<span style="color: #003399;">System</span>.<span style="color: #006633;">out</span>.<span style="color: #006633;">println</span><span style="color: #009900;">&#40;</span>evt.<span style="color: #006633;">getPropertyName</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">+</span> “ changed”<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
model <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Model<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p><strong>IObservable接口</strong></p>
<p>Eclipse绑定的核心是IObservableValue、IObservableList，通过实现这些接口对GUI和模型进行监听，我把实现了这些接口的对象成为绑定对象。包括：</p>
<ol>
<li>IObservable &#8211; 所有Observable接口的根接口，提供了对对象实例变化的监听机制</li>
<li>IObservableValue &#8211; 提供了getValue()和setValue()方法，提供了监听value改变的机制</li>
<li>IVetoableValue &#8211; 继承自IObservableValue，提供了在value变化之前进行事件处理的机制</li>
<li>IObservableCollection &#8211; 继承自java.util.Collection和IObservable</li>
<li>IObservableList &#8211; 继承自java.util.List和IObservableCollection，提供了监听list中元素添加、删除、修改事件的机制</li>
<li>IObservableSet &#8211; 继承自java.util.Set和IObservableCollection，提供了监听set中元素添加、删除、修改事件的机制</li>
<li>IObservableMap &#8211; 继承自java.util.Map和IObservable，提供了监听map中元素添加、删除、修改事件的机制</li>
</ol>
<p>其类图如下：</p>
<p style="text-align:center">
<a href="http://www.zhlwish.com/wp-content/uploads/2011/09/eclipse-jface-binding.png" rel="lightbox[775]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/09/eclipse-jface-binding-300x235.png" alt="" title="eclipse-jface-binding" width="300" height="235" class="aligncenter size-medium wp-image-777" /></a>
</p>
<p>值得注意的是上面类图中有一个ISWTObservable，封装了SWT控件，提供了监听SWT控件变动事件的机制。</p>
<p><strong>IObservable工场方法</strong></p>
<p>为简化绑定对象的创建，JFace Binding框架提供了三个工厂方法类：SWTObservables，BeansObservables和PojoObservables。</p>
<p><strong>BeansObservables</strong></p>
<p>定义于org.eclipse.core.databinding.beans包，创建实现了PropertyChangeListener的JavaBean的可观察对象, 其方法有两个系列：</p>
<ol>
<li>observeXXX(其中XXX为Value, Map, List, Set)</li>
<li>observeDetailXXX(其中XXX为Value, Map, List, Set)</li>
</ol>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">Person person <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Person<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
IObservableValue usernameObservableValue <span style="color: #339933;">=</span> BeansObservables
						.<span style="color: #006633;">observeValue</span><span style="color: #009900;">&#40;</span>person, <span style="color: #0000ff;">&quot;username&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>上面方法创建了一个监控person对象的username属性改变的IObservable对象。</p>
<p><strong>PojoObservables</strong><br />
定义于org.eclipse.core.databinding.beans包，创建基于Pojo的可观察对象，即模型对象无需实现PropertyChangeListener接口，这对于JavaBean是无侵入性的，在我们的项目中，JavaBean有JAXB从XML Schema生成，最初也是Pojo，看起来用这样的绑定方式是很好的。但是目前的版本并没有实现Pojo对象到SWT控件的绑定，即不能实现双向绑定，因此基本等于没有。</p>
<p>因此我们不得不手动的编码让每个类实现PropertyChangeListener。</p>
<p><strong>SWTObservables</strong><br />
定义于org.eclipse.jface.databinding.swt包，创建基于SWT控件的可观察对象，如创建基于txtUserName文本输入控件的值改变的观察者：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">ISWTObservableValue txtUserNameObservableValue <span style="color: #339933;">=</span> SWTObservables.<span style="color: #006633;">observeText</span><span style="color: #009900;">&#40;</span>txtUsername<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>上面代码创建的创建了一个监控txtUserName文本输入控件的输入值变化的IObservable对象。</p>
<p><strong>绑定SWT控件和Model属性</strong></p>
<p>将两个IObservable对象进行绑定是通过DataBindingContext类来实现的，这个类中定义了签名为bindValue(target, model, targetToModelUpdateValueStrategy, modelToTargetUpdateValueStrategy)的方法。此方法返回一个Binding对象。看起来挺复杂。</p>
<ol>
<li>第一个参数是绑定目标对象，经常是ISWTObservableValue对象；</li>
<li>第二个参数是绑定模型对象，经常是IObservableValue对象；</li>
<li>第三个参数是绑定对象属性值转化和校验策略，可以设置将目标对象属性值转化模型对象属性值时所有的转化器（如StringToIntegerConvertor、IntegerToStringConvertor）和对目标对象属性值的校验器（如StringToDateValidator），一般情况下是null</li>
<li>第四个参数和第三个参数刚好相反，是模型对象属性值到绑定目标对象属性值的转化和校验策略，一般情况下是null</li>
</ol>
<p>下面代码将我们之前创建的txtUserNameObservableValue和usernameObservableValue绑定起来，由于两者都是String类型，无需转化器：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">DataBindingContext bindingContext <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> DataBindingContext<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
bindingContext.<span style="color: #006633;">bindValue</span><span style="color: #009900;">&#40;</span>txtUserNameObservableValue, usernameObservableValue, <span style="color: #000066; font-weight: bold;">null</span>, <span style="color: #000066; font-weight: bold;">null</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p><strong>校验并显示错误</strong></p>
<p>如果业务需要强制要求GUI上username文本输入框必须输入不少于5个字符的字符串，那么我们就需要定义校验器：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> UsernameValidator <span style="color: #000000; font-weight: bold;">implements</span> IValidator <span style="color: #009900;">&#123;</span>
	@Override
	<span style="color: #000000; font-weight: bold;">public</span> IStatus validate<span style="color: #009900;">&#40;</span><span style="color: #003399;">Object</span> value<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>value <span style="color: #000000; font-weight: bold;">instanceof</span> <span style="color: #003399;">String</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>value.<span style="color: #006633;">toString</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">length</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">&lt;</span> <span style="color: #cc66cc;">5</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
				<span style="color: #000000; font-weight: bold;">return</span> ValidationStatus.<span style="color: #006633;">error</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;用户名长度不少于5个字符&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
			<span style="color: #009900;">&#125;</span><span style="color: #000000; font-weight: bold;">else</span><span style="color: #009900;">&#123;</span>
				<span style="color: #000000; font-weight: bold;">return</span> ValidationStatus.<span style="color: #006633;">ok</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
			<span style="color: #009900;">&#125;</span>
		<span style="color: #009900;">&#125;</span>
		<span style="color: #000000; font-weight: bold;">return</span> ValidationStatus.<span style="color: #006633;">error</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;用户名只能是字符串&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>然后我们创建一个UpdateValueStrategy，将以上定义的校验器加入到策略对象中：
</pre>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">UpdateValueStrategy strategy <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> UpdateValueStrategy<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
strategy.<span style="color: #006633;">setBeforeSetValidator</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> UsernameValidator<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #003399;">Binding</span> bindValue <span style="color: #339933;">=</span> bindingContext.<span style="color: #006633;">bindValue</span><span style="color: #009900;">&#40;</span>txtUserNameObservableValue, 
						usernameObservableValue, strategy, <span style="color: #000066; font-weight: bold;">null</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>当然，加入校验器还有一个原因是要能在界面上实时地显示校验错误，在上面代码最后一行加入下面一行代码之后就会显示错误提示，如下图所示：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">ControlDecorationSupport.<span style="color: #006633;">create</span><span style="color: #009900;">&#40;</span>bindValue, SWT.<span style="color: #006633;">TOP</span> <span style="color: #339933;">|</span> SWT.<span style="color: #006633;">LEFT</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p style="text-align:center">
<a href="http://www.zhlwish.com/wp-content/uploads/2011/09/eclipse-jface-binding-error.png" rel="lightbox[775]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/09/eclipse-jface-binding-error-300x200.png" alt="" title="eclipse-jface-binding-error" width="300" height="200" class="aligncenter size-medium wp-image-781" /></a>
</p>
<p><strong>解决“绑定针对对象实例而不是类型”提到的问题</strong></p>
<p>在前面提到，绑定针对对象实例而不是类型，即将对象model绑定到GUI界面上后，如果model对象的属性变化了，GUI界面会立刻得到通知，但是当对象本身被替换成了别的对象，绑定就会失效了。在我们的项目中有这样一个需求，先解析XML文件生成模型对象，然后将该模型对象绑定到GUI界面中，当XML文件被其他修改后，GUI界面要立即同步更新。但是问题是XML文件修改后，应用程序立即重新解析XML文件，生成的是一个新的模型对象，于是出现了之前提到的对象被替换，绑定失效的问题。这类问题在Eclipse JFace Binding被成为Master-Detail的绑定问题。</p>
<p>为了解决这类型的问题，Eclipse JFace Binding提供了WritableValue、WritableList、WritableMap和WritableSet四个类。</p>
<p><strong>WritableValue</strong></p>
<p>WritableValue是代理模式的一种实现，其内部拥有一个引用指向实际的模型对象，这样，你可以将这个代理绑定到GUI界面，例如下面的代码，就可以保证对象model到GUI界面的绑定仍然有效：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">Person person <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Person<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">private</span> WritableValue model <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> WritableValue<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
model.<span style="color: #006633;">setValue</span><span style="color: #009900;">&#40;</span>person<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
model.<span style="color: #006633;">addPropertyChangeListener</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">this</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
person <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Person<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
model.<span style="color: #006633;">setValue</span><span style="color: #009900;">&#40;</span>person<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>对于person的属性username和txtUsername文本输入框之间的绑定现在需要做如下修改：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">IObservableValue usernameObservableValue <span style="color: #339933;">=</span> BeansObservables
			.<span style="color: #006633;">observeDetailsValue</span><span style="color: #009900;">&#40;</span>model, <span style="color: #0000ff;">&quot;username&quot;</span>, <span style="color: #003399;">String</span>.<span style="color: #000000; font-weight: bold;">class</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>第一个参数是所谓的master对象，第二个参数是属性名称，第三个是属性的类型（直接写null也行）</p>
<p><strong>小结</strong><br />
到目前为止，Eclipse JFace Binding的核心部分基本讲解完毕，对于简单对象的绑定应该是没有问题，不过除了简单控件之外，Eclipse中还会大量使用TableView、ListView、TreeView这样的viewer，他们就不是简单的绑定一个JavaBean属性，而是需要绑定一个List/Tree或者一个Map，又复杂起来了，下文再讲。</p>
<p><strong>参考</strong><br />
<a href="http://java.sun.com/developer/onlineTraining/Beans/JBeansAPI/shortcourse.html" target="_blank">http://java.sun.com/developer/onlineTraining/Beans/JBeansAPI/shortcourse.html</a><br />
<a href="http://wiki.eclipse.org/index.php/JFace_Data_Binding" target="_blank">http://wiki.eclipse.org/index.php/JFace_Data_Binding</a><br />
<a href="http://www.vogella.de/articles/EclipseDataBinding/article.html" target="_blank">http://www.vogella.de/articles/EclipseDataBinding/article.html</a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/oC_HMCcgOHo" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-2/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-2/</feedburner:origLink></item>
		<item>
		<title>Eclipse JFace Binding/绑定 (1)</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/QAFQjULU0jE/</link>
		<comments>http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-1/#comments</comments>
		<pubDate>Sat, 17 Sep 2011 08:08:55 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Eclispe RCP]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=767</guid>
		<description><![CDATA[binding这个词挺有意思的，中文意译为“绑定”，音译也可以是”绑定“，但是“绑定”这个词看起来又不是像“巴士”这样的词一样属于外来词。我深深地感觉第一个把binding翻译成“绑定”的人当时一定感觉很好。 为什么需要“绑定” 在MVC架构中，View（GUI）上的控件的值来源于Model，用户在View上的操作也需要更新到Model。由于桌面应用程序的实时响应特性，后台服务（如数字校验、根据单价和数量计算总价）对Model的更新也需要实时通过View反馈给用户。 Java应用中，Model和View都是相互独立的JavaBean。JavaBean API中，Bean之间的通信通过事件传递实现。事件在一方属性变化时被创建，然后传递给响应变化的一方，后者从事件对象中获取事件信息，进而调用相应的方法实现响应操作。 一般情况下，GUI操作以及Model的属性变化被封装成一个事件对象（Event），事件对象一般包括了事件发生的来源（控件或者模型），变化之前的值和变化之后的值。如对于JavaBean API中定义的类PropertyChangeEvent，有source、propertyName、oldValue、newValue四个属性。 模拟Model和View的“绑定” GUI和Model的绑定使用观察者模式来实现，也就是常说的Observable模式，不过在JavaBean的事件模型里面叫做Listener模式。不同的叫法实质是一样的，Observable是针对被观察的对象而言，Listener则是针对观察其他对象的对象而言。 Observable模式在Java API中有支持，可以直接继承java.util.Observable来实现一个被观察类，通过实现java.util.Observer接口实现观察者，然后调用Observable.addObserver(Observer)方法来建立消息发送渠道。这种方法存在的问题就是，被观察者类必须继承Observable类，由于Java是单继承，因此这个类就不能继承其他类了。 JavaBean API中提供IPropertyChangeListener接口和PropertyChangeSupport类来实现Bean之间的事件通信。我们创建如下两个类： Window：模拟GUI中的窗口，包括txtUsername和txtPassword两个文本输入框 Model：模式实体类，包括username和password两个字符串属性 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 &#8230; <a href="http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-1/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/duG1cnKMtbIMXei5TlLRzuK_pZI/0/da"><img src="http://feedads.g.doubleclick.net/~a/duG1cnKMtbIMXei5TlLRzuK_pZI/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/duG1cnKMtbIMXei5TlLRzuK_pZI/1/da"><img src="http://feedads.g.doubleclick.net/~a/duG1cnKMtbIMXei5TlLRzuK_pZI/1/di" border="0" ismap="true"></img></a></p><p>binding这个词挺有意思的，中文意译为“绑定”，音译也可以是”绑定“，但是“绑定”这个词看起来又不是像“巴士”这样的词一样属于外来词。我深深地感觉第一个把binding翻译成“绑定”的人当时一定感觉很好。</p>
<p><strong>为什么需要“绑定”</strong></p>
<p>在MVC架构中，View（GUI）上的控件的值来源于Model，用户在View上的操作也需要更新到Model。由于桌面应用程序的实时响应特性，后台服务（如数字校验、根据单价和数量计算总价）对Model的更新也需要实时通过View反馈给用户。<br />
<span id="more-767"></span><br />
Java应用中，Model和View都是相互独立的JavaBean。JavaBean API中，Bean之间的通信通过事件传递实现。事件在一方属性变化时被创建，然后传递给响应变化的一方，后者从事件对象中获取事件信息，进而调用相应的方法实现响应操作。</p>
<p>一般情况下，GUI操作以及Model的属性变化被封装成一个事件对象（Event），事件对象一般包括了事件发生的来源（控件或者模型），变化之前的值和变化之后的值。如对于JavaBean API中定义的类PropertyChangeEvent，有source、propertyName、oldValue、newValue四个属性。</p>
<p><strong>模拟Model和View的“绑定”</strong></p>
<p>GUI和Model的绑定使用观察者模式来实现，也就是常说的Observable模式，不过在JavaBean的事件模型里面叫做Listener模式。不同的叫法实质是一样的，Observable是针对被观察的对象而言，Listener则是针对观察其他对象的对象而言。</p>
<p>Observable模式在Java API中有支持，可以直接继承java.util.Observable来实现一个被观察类，通过实现java.util.Observer接口实现观察者，然后调用Observable.addObserver(Observer)方法来建立消息发送渠道。这种方法存在的问题就是，被观察者类必须继承Observable类，由于Java是单继承，因此这个类就不能继承其他类了。</p>
<p>JavaBean API中提供IPropertyChangeListener接口和PropertyChangeSupport类来实现Bean之间的事件通信。我们创建如下两个类：</p>
<ol>
<li>Window：模拟GUI中的窗口，包括txtUsername和txtPassword两个文本输入框</li>
<li>Model：模式实体类，包括username和password两个字符串属性</li>
</ol>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.binding</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.beans.PropertyChangeListener</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.beans.PropertyChangeSupport</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> <span style="color: #003399;">Window</span><span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">PropertyChangeSupport</span> pcs <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">PropertyChangeSupport</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">this</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">String</span> txtUsername<span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">String</span> txtPassword<span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">String</span> getTxtUsername<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> txtUsername<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setTxtUsername<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> txtUsername<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		pcs.<span style="color: #006633;">firePropertyChange</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;txtUsername&quot;</span>, <span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">txtUsername</span>, 
				<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">txtUsername</span> <span style="color: #339933;">=</span> txtUsername<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">String</span> getTxtPassword<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> txtPassword<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setTxtPassword<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> txtPassword<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		pcs.<span style="color: #006633;">firePropertyChange</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;txtPassword&quot;</span>, <span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">txtPassword</span>, 
				<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">txtPassword</span> <span style="color: #339933;">=</span> txtPassword<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> addPropertyChangeListener<span style="color: #009900;">&#40;</span><span style="color: #003399;">PropertyChangeListener</span> listener<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		pcs.<span style="color: #006633;">addPropertyChangeListener</span><span style="color: #009900;">&#40;</span>listener<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> removePropertyChangeListener<span style="color: #009900;">&#40;</span><span style="color: #003399;">PropertyChangeListener</span> listener<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		pcs.<span style="color: #006633;">removePropertyChangeListener</span><span style="color: #009900;">&#40;</span>listener<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>Window类中，当调用set方法设置值的时候，同时调用firePropertyChange()方法通知监听器（listener）。而且提供addPropertyChangeListener()和removePropertyChangeListener()两个方法添加和删除监听器。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.binding</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.beans.PropertyChangeEvent</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.beans.PropertyChangeListener</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.beans.PropertyChangeSupport</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> Model <span style="color: #000000; font-weight: bold;">implements</span> <span style="color: #003399;">PropertyChangeListener</span><span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">String</span> username<span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">String</span> password<span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">String</span> getUsername<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> username<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setUsername<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> username<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">username</span> <span style="color: #339933;">=</span> username<span style="color: #339933;">;</span>
		<span style="color: #003399;">System</span>.<span style="color: #006633;">out</span>.<span style="color: #006633;">println</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;username update to : &quot;</span> <span style="color: #339933;">+</span> username<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">String</span> getPassword<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> password<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setPassword<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> password<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">password</span> <span style="color: #339933;">=</span> password<span style="color: #339933;">;</span>
		<span style="color: #003399;">System</span>.<span style="color: #006633;">out</span>.<span style="color: #006633;">println</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;password update to : &quot;</span> <span style="color: #339933;">+</span> password<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> propertyChange<span style="color: #009900;">&#40;</span><span style="color: #003399;">PropertyChangeEvent</span> evt<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #003399;">System</span>.<span style="color: #006633;">out</span>.<span style="color: #006633;">println</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;Model has recived the change&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>evt.<span style="color: #006633;">getPropertyName</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">equals</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;txtUsername&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">setUsername</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span><span style="color: #009900;">&#41;</span> evt.<span style="color: #006633;">getNewValue</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span><span style="color: #000000; font-weight: bold;">else</span> <span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>evt.<span style="color: #006633;">getPropertyName</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">equals</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;txtPassword&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">setPassword</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span><span style="color: #009900;">&#41;</span> evt.<span style="color: #006633;">getNewValue</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>Model类实现了PropertyChangeListener接口，因此必须实现PropertyChangeListener中定义的propertyChange()方法。在此方法中，根据PropertyChangeEvent对象中携带的不同信息进行处理。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.binding</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> Main <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000066; font-weight: bold;">void</span> main<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> args<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #003399;">Window</span> w <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Window</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		Model m <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Model<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		w.<span style="color: #006633;">addPropertyChangeListener</span><span style="color: #009900;">&#40;</span>m<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		w.<span style="color: #006633;">setTxtPassword</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;new password&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>Main充当了控制器的作用，创建Window和Model，然后设置Model监听Window的改动，之后模拟用户通过GUI修改txtPassword，程序的结果输出如下：</p>
<pre>
Model has recived the change
password update to : new password
</pre>
<p><strong>模拟双向绑定</strong></p>
<p>上面仅仅实现了单项的绑定，即View的改变会告知Model，但是Model的改变不会被告知View。为实现双向绑定，需要向GUI和Model相互注册为对方的Listener，以响应对方的改动。</p>
<p>因此，此时不仅Model需要实现PropertyChangeListener，Window也需要实现该接口，需要实现响应对方改动的处理方法，具体代码比较长，当然这也是在具体应用的时候不可能直接使用此API的原因&#8211;实现代码太长了。长长的代码请下载<a href="http://zhlwish.googlecode.com/files/eclipse-binding-1.tar.gz">http://zhlwish.googlecode.com/files/eclipse-binding-1.tar.gz</a></p>
<p><strong>小结</strong></p>
<p>由于事件处理函数集中于propertyChange()方法，需要根据不同的属性变化调用不同的方法处理，会导致该方法冗长繁琐，这是一个问题。另外，在从Model到View，从View到Model会涉及一些数据类型转换，和数据校验，这部分是需要像你我这样的程序猿去自己实现的，对于我这样的懒人来讲也是一个问题。第三，在每个set方法里面去编写firePropertyChange()这样的方法我也觉得很繁琐，而且容易出错，这也是一个问题。</p>
<p>最后，最重要的，这只是一个模拟，还没有涉及到AWT/Swing或者SWT/JFace中的控件的事件处理，什么onChange(),onSelection()……，必然的还会实现很多ActionListener这样的匿名内部类，oh，gosh！</p>
<p>不过，看起来Eclipse的开发人员也意识到了这个问题，在JFace中已经加入了Binding这样的组件，我们可以直接使用这样一些组件方便的快捷的实现Model到View的绑定。</p>
<p>ps.有什么方法可以很好的表现观察着模式么，UML类图只是静态关系，看不来任何实质的，因为涉及对象与对象的交互，可能序列图会更好，不过我没有尝试去画过。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/QAFQjULU0jE" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-1/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/09/17/eclipse-jface-binding-1/</feedburner:origLink></item>
		<item>
		<title>一步一步实现GEF – 9</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/BvQwas5jT7w/</link>
		<comments>http://www.zhlwish.com/2011/09/09/gef-step-by-step-9/#comments</comments>
		<pubDate>Fri, 09 Sep 2011 06:32:48 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[GEF]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=747</guid>
		<description><![CDATA[很长一段时间没有继续写了，很多东西都快忘记了，赶紧捡起来 让你的GEF图元可以拖动和缩放 拖动算是最简单的用户交互吧，不过麻雀虽小，肝胆俱全，不理解其原理和设计思路，很难谈得上去应用，但是要理解这一整套交互模型又有相当的难度，本文虽重在实践，这里也略做介绍。后文中所述图元指EditPart对象实例。 GEF用户交互有四个重要的概念：Command，Policy，Request，Role GEF图元对于用户操作的响应（具体的执行操作）被称为Command，这是命令模式的典型实现 GEF图元对于用户操作采用何种响应（操作->响应）被称为EditPolicy，这是策略模式的典型实现，Policy可以认为是一个Map，输入一个Request，输出其对应的Command 用户对图元的操作（拖拽、选择）被称为Request 用户对图元的操作是可以分类的，这个类型被称为Role。比如拖动图元移动位置，拖动图元边框改变图元大小是影响布局的操作，称为LAYOUT_ROLE；双击图元修改图元上的文字信息，双击连线上的问题修改连线的说明，这些都是直接对图元进行修改的操作，称为DIRECT_EDIT_ROLE……，这样的操作类型有很多，以后有机会再进行系统的总结。 对于用户的操作，图元使用那种响应策略（是边框变粗、还是Label变成Input接受用户输入），取决于图元上注册的事件响应类型（Role），当然我们可以向图元同时注册多个响应策略，用于响应不同的用户输入： installEditPolicy&#40;EditPolicy.LAYOUT_ROLE, new DiagramLayoutEditPolicy&#40;&#41;&#41;; 关于此installEditPolicy()方法，我同组的小牛分析得比较透彻，看他：http://www.thankcreate.com/java/357 OK, 下面我们开始编码。 创建Command 首先创建一个Command类，用于响应用户的拖拽操作，com.zhlwish.learngef.command.AjustNodeConstraintCommand继承自org.eclipse.gef.commands.Command，代码如下： 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 &#8230; <a href="http://www.zhlwish.com/2011/09/09/gef-step-by-step-9/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/1qHznNGf6-wenCDtxlC4v-39hUY/0/da"><img src="http://feedads.g.doubleclick.net/~a/1qHznNGf6-wenCDtxlC4v-39hUY/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/1qHznNGf6-wenCDtxlC4v-39hUY/1/da"><img src="http://feedads.g.doubleclick.net/~a/1qHznNGf6-wenCDtxlC4v-39hUY/1/di" border="0" ismap="true"></img></a></p><p>很长一段时间没有继续写了，很多东西都快忘记了，赶紧捡起来</p>
<p><strong>让你的GEF图元可以拖动和缩放</strong></p>
<p>拖动算是最简单的用户交互吧，不过麻雀虽小，肝胆俱全，不理解其原理和设计思路，很难谈得上去应用，但是要理解这一整套交互模型又有相当的难度，本文虽重在实践，这里也略做介绍。后文中所述图元指EditPart对象实例。<br />
<span id="more-747"></span><br />
GEF用户交互有四个重要的概念：Command，Policy，Request，Role</p>
<ol>
<li>GEF图元对于用户操作的响应（具体的执行操作）被称为Command，这是<a href="http://terrylee.cnblogs.com/archive/2006/07/17/Command_Pattern.html" title="命令模式" target="_blank">命令模式</a>的典型实现
<p style="text-align: center"><a href="http://www.zhlwish.com/wp-content/uploads/2011/09/command_inherit.jpg" rel="lightbox[747]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/09/command_inherit-300x272.jpg" alt="" title="GEF Command继承关系" width="300" height="272" class="aligncenter size-medium wp-image-755" /></a></p>
</li>
<li>GEF图元对于用户操作采用何种响应（操作->响应）被称为EditPolicy，这是<a href="http://www.cnblogs.com/justinw/archive/2007/02/06/641414.html" title="策略模式" target="_blank">策略模式</a>的典型实现，Policy可以认为是一个Map，输入一个Request，输出其对应的Command
<p style="text-align: center"><a href="http://www.zhlwish.com/wp-content/uploads/2011/09/editpolicy.jpg" rel="lightbox[747]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/09/editpolicy-300x183.jpg" alt="" title="Eclipse EditPolicy" width="300" height="183" class="aligncenter size-medium wp-image-757" /></a></p>
</li>
<li>用户对图元的操作（拖拽、选择）被称为Request
<p style="text-align: center"><a href="http://www.zhlwish.com/wp-content/uploads/2011/09/eclipse-request.png" rel="lightbox[747]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/09/eclipse-request-245x300.png" alt="" title="Eclipse Request" width="245" height="300" class="aligncenter size-medium wp-image-758" /></a></p>
</li>
<li>用户对图元的操作是可以分类的，这个类型被称为Role。比如拖动图元移动位置，拖动图元边框改变图元大小是影响布局的操作，称为LAYOUT_ROLE；双击图元修改图元上的文字信息，双击连线上的问题修改连线的说明，这些都是直接对图元进行修改的操作，称为DIRECT_EDIT_ROLE……，这样的操作类型有很多，以后有机会再进行系统的总结。</li>
</ol>
<p>对于用户的操作，图元使用那种响应策略（是边框变粗、还是Label变成Input接受用户输入），取决于图元上注册的事件响应类型（Role），当然我们可以向图元同时注册多个响应策略，用于响应不同的用户输入：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">installEditPolicy<span style="color: #009900;">&#40;</span>EditPolicy.<span style="color: #006633;">LAYOUT_ROLE</span>, <span style="color: #000000; font-weight: bold;">new</span> DiagramLayoutEditPolicy<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>关于此installEditPolicy()方法，我同组的小牛分析得比较透彻，看他：<a href="http://www.thankcreate.com/java/357" target="_blank">http://www.thankcreate.com/java/357</a></p>
<p>OK, 下面我们开始编码。</p>
<p><strong>创建Command</strong></p>
<p>首先创建一个Command类，用于响应用户的拖拽操作，com.zhlwish.learngef.command.AjustNodeConstraintCommand继承自org.eclipse.gef.commands.Command，代码如下：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> AjustNodeConstraintCommand <span style="color: #000000; font-weight: bold;">extends</span> Command <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> GraphicalEditPart editPart<span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">Rectangle</span> newBounds, oldBounds<span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> AjustNodeConstraintCommand<span style="color: #009900;">&#40;</span>EditPart child, <span style="color: #003399;">Object</span> constraint<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		editPart <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span>GraphicalEditPart<span style="color: #009900;">&#41;</span> child<span style="color: #339933;">;</span>
		newBounds <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span><span style="color: #003399;">Rectangle</span><span style="color: #009900;">&#41;</span> constraint<span style="color: #339933;">;</span>
		oldBounds <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Rectangle</span><span style="color: #009900;">&#40;</span>editPart.<span style="color: #006633;">getFigure</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getBounds</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> execute<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		redo<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> redo<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		GraphicalEditPart parent <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span>GraphicalEditPart<span style="color: #009900;">&#41;</span> editPart.<span style="color: #006633;">getParent</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		parent.<span style="color: #006633;">setLayoutConstraint</span><span style="color: #009900;">&#40;</span>editPart, editPart.<span style="color: #006633;">getFigure</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>, newBounds<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> undo<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		GraphicalEditPart parent <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span>GraphicalEditPart<span style="color: #009900;">&#41;</span> editPart.<span style="color: #006633;">getParent</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		parent.<span style="color: #006633;">setLayoutConstraint</span><span style="color: #009900;">&#40;</span>editPart, editPart.<span style="color: #006633;">getFigure</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>, oldBounds<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>这段代码很容易理解，将之前的constraint保存起来，将新的contraint应用到图元上，GEF的图形API以后有机会再详述。</p>
<p><strong>创建Policy</strong></p>
<p>由于我们现在处理的是布局，因此创建com.zhlwish.learngef.policy.DiagramLayoutEditPolicy，使其继承org.eclipse.gef.editpolicies.XYLayoutEditPolicy，由于XYLayoutEditPolicy已经实现了底层的一些细节（getCommand()方法实现了根据Request类型查找对应的Command），我们只需要重写createChangeConstraintCommand()即可，此方法默认返回null，因而图元不会执行拖拽和缩放请求的。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> DiagramLayoutEditPolicy <span style="color: #000000; font-weight: bold;">extends</span> XYLayoutEditPolicy <span style="color: #009900;">&#123;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">protected</span> Command getCreateCommand<span style="color: #009900;">&#40;</span>CreateRequest request<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> <span style="color: #000066; font-weight: bold;">null</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">protected</span> Command createChangeConstraintCommand<span style="color: #009900;">&#40;</span>
			ChangeBoundsRequest request, EditPart child, <span style="color: #003399;">Object</span> constraint<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>child <span style="color: #000000; font-weight: bold;">instanceof</span> NodePart<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>constraint <span style="color: #000000; font-weight: bold;">instanceof</span> <span style="color: #003399;">Rectangle</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
				<span style="color: #000000; font-weight: bold;">return</span> <span style="color: #000000; font-weight: bold;">new</span> AjustNodeConstraintCommand<span style="color: #009900;">&#40;</span>child, constraint<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
			<span style="color: #009900;">&#125;</span>
		<span style="color: #009900;">&#125;</span>
		<span style="color: #000000; font-weight: bold;">return</span> <span style="color: #000000; font-weight: bold;">super</span>.<span style="color: #006633;">createChangeConstraintCommand</span><span style="color: #009900;">&#40;</span>request, child, constraint<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p><strong>安装Policy</strong></p>
<p>“安装”这个字眼有点让人不安，这里这么说主要是因为实现此功能的方法叫installEditPolicy()，暂且就这么叫吧。</p>
<p>如果我没记错的话，com.zhlwish.learngef.part.DiagramPart类中应该有个空的方法叫createEditPolicies()，在里面添加一个个语句，看见没installEditPolicy()第一个参数就是我们所说的请求的类型（Role）：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">protected</span> <span style="color: #000066; font-weight: bold;">void</span> createEditPolicies<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	installEditPolicy<span style="color: #009900;">&#40;</span>EditPolicy.<span style="color: #006633;">LAYOUT_ROLE</span>, <span style="color: #000000; font-weight: bold;">new</span> DiagramLayoutEditPolicy<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p><strong>运行</strong></p>
<p>到目前为止，所需要的编码工作就已经完成了，运行程序，此时你会发现已经可以对图元进行移动了，鼠标移动到边框上还可以缩放图元，和下面的图一样。</p>
<p style="text-align: center">
<a href="http://www.zhlwish.com/wp-content/uploads/2011/09/drag-and-resize-editpart.png" rel="lightbox[747]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/09/drag-and-resize-editpart-300x186.png" alt="" title="拖动和缩放图元" width="300" height="186" class="aligncenter size-medium wp-image-750" /></a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/BvQwas5jT7w" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/09/09/gef-step-by-step-9/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/09/09/gef-step-by-step-9/</feedburner:origLink></item>
		<item>
		<title>Ubuntu设置双拼输入法</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/6xmvz7VQQVs/</link>
		<comments>http://www.zhlwish.com/2011/08/26/ubuntu-ibus-double-pinyin/#comments</comments>
		<pubDate>Thu, 25 Aug 2011 17:02:42 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[ubuntu]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=732</guid>
		<description><![CDATA[一直比较喜欢ibus，毕竟是官方支持，而且的确比较简单，不用像其他的输入法，配置繁杂不说，还经常出问题。添加了中文语言支持时会自动安装ibus，然后添加拼音输入法就可以用了。 最近新安装了Ubuntu11.04，发现找不到设置双拼的地方了，经过探索发现，首先在ibus首选项中修改“Show language panel”为“always”。 然后在任意能输入的地方，Control+space切换输入法，这时出来一个工具条： 点击齿轮图标（Preference）,打开ibus-pinyin选项，切换到Pinyin mode选项卡，然后选择”Double pinyin”即可，默认双拼方案为MSPY，我猜是微软双拼，ZRM就是我用的自然码方案啦。]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/KvAbB5r9C4o-RedYz_UxEUCjtoY/0/da"><img src="http://feedads.g.doubleclick.net/~a/KvAbB5r9C4o-RedYz_UxEUCjtoY/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/KvAbB5r9C4o-RedYz_UxEUCjtoY/1/da"><img src="http://feedads.g.doubleclick.net/~a/KvAbB5r9C4o-RedYz_UxEUCjtoY/1/di" border="0" ismap="true"></img></a></p><p>一直比较喜欢ibus，毕竟是官方支持，而且的确比较简单，不用像其他的输入法，配置繁杂不说，还经常出问题。添加了中文语言支持时会自动安装ibus，然后添加拼音输入法就可以用了。<br />
<span id="more-732"></span><br />
最近新安装了Ubuntu11.04，发现找不到设置双拼的地方了，经过探索发现，首先在ibus首选项中修改“Show language panel”为“always”。</p>
<p style="text-align:center"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/ibus-preference.png" rel="lightbox[732]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/08/ibus-preference-248x300.png" alt="" title="ibus Preference" width="248" height="300" class="aligncenter size-medium wp-image-734" /></a>
</p>
<p>然后在任意能输入的地方，Control+space切换输入法，这时出来一个工具条：</p>
<p style="text-align:center"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/ibus-language-panel.png" rel="lightbox[732]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/08/ibus-language-panel.png" alt="" title="ibus Language Panel" width="220" height="32" class="aligncenter size-full wp-image-735" /></a></p>
<p>点击齿轮图标（Preference）,打开ibus-pinyin选项，切换到Pinyin mode选项卡，然后选择”Double pinyin”即可，默认双拼方案为MSPY，我猜是微软双拼，ZRM就是我用的自然码方案啦。</p>
<p style="text-align:center"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/ibus-pinyin-preference.png" rel="lightbox[732]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/08/ibus-pinyin-preference-229x300.png" alt="" title="ibus Pinyin Preferences" width="229" height="300" class="aligncenter size-medium wp-image-737" /></a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/6xmvz7VQQVs" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/26/ubuntu-ibus-double-pinyin/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/26/ubuntu-ibus-double-pinyin/</feedburner:origLink></item>
		<item>
		<title>一步一步实现GEF – 8</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/ScdtgVbA_nw/</link>
		<comments>http://www.zhlwish.com/2011/08/22/gef-step-by-step-8/#comments</comments>
		<pubDate>Mon, 22 Aug 2011 13:54:05 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[GEF]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=715</guid>
		<description><![CDATA[将View中的图形移到编辑器中 在View中是不能对图形进行移动、修改大小的，需要对图形进行修改必须使用Editor，因此，我们首先创建一个GEF编辑器，然后将图形显示在编辑器中。 创建编辑器 打开plugin.xml，打开Extensions标签页，添加org.eclipse.ui.editors扩展，然后添加一个Editor，Name为Nodes GEF Editor，Extensions为gef，如下图所示: 创建NodeGefEditor类，继承自GraphicalEditorWithFlyoutPalette，代码如下： 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 package com.zhlwish.learngef.editor; &#160; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.gef.DefaultEditDomain; import org.eclipse.gef.palette.PaletteRoot; import org.eclipse.gef.ui.parts.GraphicalEditorWithFlyoutPalette; &#8230; <a href="http://www.zhlwish.com/2011/08/22/gef-step-by-step-8/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/qOnBQYQ-mfC8Lr6Vf2M8QdCHX7w/0/da"><img src="http://feedads.g.doubleclick.net/~a/qOnBQYQ-mfC8Lr6Vf2M8QdCHX7w/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/qOnBQYQ-mfC8Lr6Vf2M8QdCHX7w/1/da"><img src="http://feedads.g.doubleclick.net/~a/qOnBQYQ-mfC8Lr6Vf2M8QdCHX7w/1/di" border="0" ismap="true"></img></a></p><p><strong>将View中的图形移到编辑器中</strong></p>
<p>在View中是不能对图形进行移动、修改大小的，需要对图形进行修改必须使用Editor，因此，我们首先创建一个GEF编辑器，然后将图形显示在编辑器中。</p>
<p><strong>创建编辑器</strong></p>
<p>打开plugin.xml，打开Extensions标签页，添加org.eclipse.ui.editors扩展，然后添加一个Editor，Name为Nodes GEF Editor，Extensions为gef，如下图所示:<br />
<span id="more-715"></span></p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图09.png" rel="lightbox[715]"><img class="aligncenter size-medium wp-image-717" title="创建编辑器" src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图09-300x154.png" alt="" width="300" height="154" /></a></p>
<p>创建NodeGefEditor类，继承自GraphicalEditorWithFlyoutPalette，代码如下：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.editor</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.core.runtime.IProgressMonitor</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.gef.DefaultEditDomain</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.gef.palette.PaletteRoot</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.gef.ui.parts.GraphicalEditorWithFlyoutPalette</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> NodeGefEditor <span style="color: #000000; font-weight: bold;">extends</span> GraphicalEditorWithFlyoutPalette <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> NodeGefEditor<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">protected</span> PaletteRoot getPaletteRoot<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> <span style="color: #000066; font-weight: bold;">null</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> doSave<span style="color: #009900;">&#40;</span>IProgressMonitor monitor<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p><strong>设置EditDomain</strong></p>
<p>首先在构造函数中设置EditDomain，如下：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> NodeGefEditor<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	setEditDomain<span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> DefaultEditDomain<span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">this</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p><strong>显示图形</strong></p>
<p>接着覆盖间接父类GraphicalEditor的configureGraphicalViewer()方法，设置EditPartFactory和RootEditPart，可以和<a href="http://www.zhlwish.com/2011/08/12/gef-step-by-step-4/" title="一步一步实现GEF – 4" target="_blank">一步一步实现GEF – 4</a>中的NodeGefView类的代码进行比较，代码如下：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;">@Override
<span style="color: #000000; font-weight: bold;">protected</span> <span style="color: #000066; font-weight: bold;">void</span> configureGraphicalViewer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">super</span>.<span style="color: #006633;">configureGraphicalViewer</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	GraphicalViewer viewer <span style="color: #339933;">=</span> getGraphicalViewer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	viewer.<span style="color: #006633;">setEditPartFactory</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> PartFactory<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	ScalableFreeformRootEditPart rootEditPart <span style="color: #339933;">=</span> 
		<span style="color: #000000; font-weight: bold;">new</span> ScalableFreeformRootEditPart<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	viewer.<span style="color: #006633;">setRootEditPart</span><span style="color: #009900;">&#40;</span>rootEditPart<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>为了能尽快的在编辑器中显示图形，我们直接通过GraphicalViewer的setContents()方法显示通过硬编码创建的一个Diagram，如下：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;">@Override
<span style="color: #000000; font-weight: bold;">protected</span> <span style="color: #000066; font-weight: bold;">void</span> initializeGraphicalViewer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">super</span>.<span style="color: #006633;">initializeGraphicalViewer</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	GraphicalViewer viewer <span style="color: #339933;">=</span> getGraphicalViewer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	Diagram diagram <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Diagram<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	Node node <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Node<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node.<span style="color: #006633;">setText</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;测试节点&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node.<span style="color: #006633;">setLocation</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Point</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">10</span>, <span style="color: #cc66cc;">10</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	diagram.<span style="color: #006633;">addNode</span><span style="color: #009900;">&#40;</span>node<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	Node node2 <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Node<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node2.<span style="color: #006633;">setText</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;测试节点&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node2.<span style="color: #006633;">setLocation</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Point</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">100</span>, <span style="color: #cc66cc;">170</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	diagram.<span style="color: #006633;">addNode</span><span style="color: #009900;">&#40;</span>node2<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #003399;">Connection</span> conn <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Connection</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	conn.<span style="color: #006633;">connect</span><span style="color: #009900;">&#40;</span>node, node2<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	viewer.<span style="color: #006633;">setContents</span><span style="color: #009900;">&#40;</span>diagram<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>这段代码和<a href="http://www.zhlwish.com/2011/08/12/gef-step-by-step-6/" title="一步一步实现GEF – 6" target="_blank">一步一步实现GEF – 6</a>是不是又完全一样呢？</p>
<p><strong>运行</strong></p>
<p>好啦，到了这里可以运行项目了，运行后，创建一个名称任意（我的叫testgef）的项目，然后在项目中创建一个test.gef（名称随意，后缀名只能是gef）的文件，然后双击打开这个文件，应该看到下面的这个图：</p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图11.png" rel="lightbox[715]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图11-300x182.png" alt="" title="显示出了图形的GEF编辑器" width="300" height="182" class="aligncenter size-medium wp-image-720" /></a></p>
<p><strong>工具条</strong><br />
编辑器的右边，有个三角形，鼠标移动上去，就会有个工具条展开，如下图所示：
</p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图10.png" rel="lightbox[715]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图10-300x232.png" alt="" title="展开了工具条的GEF编辑器" width="300" height="232" class="aligncenter size-medium wp-image-722" /></a></p>
<p>当然，还可以通过以下方法来设置工具条的样子，如显示在编辑器的左边而不是右边，或者让工具条在编辑器打开的时候就显示等。不过这个并不重要，因此，此处仅仅提示，并不深入说明，有兴趣可以自己看代码。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;">getPalettePreferences<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">setDockLocation</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
getPalettePreferences<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">setPaletteState</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
getPalettePreferences<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">setPaletteWidth</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></td></tr></table></div>

<p><strong>无法拖拽</strong></p>
<p>如果你比较好奇，肯定会尝试去用鼠标拖动图形，但是很遗憾，拖不动。怎么样才能使用鼠标拖动图形，移动图形到任何位置呢，敬请期待下文。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/ScdtgVbA_nw" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/22/gef-step-by-step-8/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/22/gef-step-by-step-8/</feedburner:origLink></item>
		<item>
		<title>一步一步实现GEF – 7</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/A5E4ichzxsc/</link>
		<comments>http://www.zhlwish.com/2011/08/22/gef-step-by-step-7/#comments</comments>
		<pubDate>Mon, 22 Aug 2011 13:53:53 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[GEF]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=706</guid>
		<description><![CDATA[添加Tooltips 我们希望用户将鼠标移动到图元上时，能够友好的显示图元的一些详细信息，可以通过Tooltip的方法实现。GEF中Figure类中定义了图元的Tooltip，其类型为IFigure，因此我们可以创建一个Label，然后将Label作为图元的Tooltip显示。 在NodeFigure类中添加一个私有方法createToolTip()，将结点的位置和背景的颜色显示给用户。 1 2 3 4 5 6 7 private Figure createToolTip&#40;&#41;&#123; Label tooltip = new Label&#40;&#41;; String color = model.getColor&#40;&#41;.toString&#40;&#41;; String loc = model.getLocation&#40;&#41;.toString&#40;&#41;; tooltip.setText&#40;color + &#34;, &#34; + loc&#41;; return tooltip; &#125; 之后在NodeFigure的构造函数中调用setToolTip()给图元设置Tooltip（下面代码的倒数第二行） 1 2 3 4 &#8230; <a href="http://www.zhlwish.com/2011/08/22/gef-step-by-step-7/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/kHSbfuVop4nIZWdn-P_1epAxHco/0/da"><img src="http://feedads.g.doubleclick.net/~a/kHSbfuVop4nIZWdn-P_1epAxHco/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/kHSbfuVop4nIZWdn-P_1epAxHco/1/da"><img src="http://feedads.g.doubleclick.net/~a/kHSbfuVop4nIZWdn-P_1epAxHco/1/di" border="0" ismap="true"></img></a></p><p><strong>添加Tooltips</strong></p>
<p>我们希望用户将鼠标移动到图元上时，能够友好的显示图元的一些详细信息，可以通过Tooltip的方法实现。GEF中Figure类中定义了图元的Tooltip，其类型为IFigure，因此我们可以创建一个Label，然后将Label作为图元的Tooltip显示。<br />
在NodeFigure类中添加一个私有方法createToolTip()，将结点的位置和背景的颜色显示给用户。<br />
<span id="more-706"></span></p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">private</span> Figure createToolTip<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
	<span style="color: #003399;">Label</span> tooltip <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Label</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #003399;">String</span> color <span style="color: #339933;">=</span> model.<span style="color: #006633;">getColor</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">toString</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #003399;">String</span> loc <span style="color: #339933;">=</span> model.<span style="color: #006633;">getLocation</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">toString</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	tooltip.<span style="color: #006633;">setText</span><span style="color: #009900;">&#40;</span>color <span style="color: #339933;">+</span> <span style="color: #0000ff;">&quot;, &quot;</span> <span style="color: #339933;">+</span> loc<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">return</span> tooltip<span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>之后在NodeFigure的构造函数中调用setToolTip()给图元设置Tooltip（下面代码的倒数第二行）</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> NodeFigure<span style="color: #009900;">&#40;</span>Node node<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	model <span style="color: #339933;">=</span> node<span style="color: #339933;">;</span>
&nbsp;
	label <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Label</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	label.<span style="color: #006633;">setText</span><span style="color: #009900;">&#40;</span>model.<span style="color: #006633;">getText</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	label.<span style="color: #006633;">setForegroundColor</span><span style="color: #009900;">&#40;</span><span style="color: #003399;">Activator</span>.<span style="color: #006633;">getDefault</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getColor</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> RGB<span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">0</span>, <span style="color: #cc66cc;">0</span>, <span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	add<span style="color: #009900;">&#40;</span>label<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #666666; font-style: italic;">//通过模型获得位置</span>
	<span style="color: #003399;">Point</span> loc <span style="color: #339933;">=</span> model.<span style="color: #006633;">getLocation</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	setBounds<span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Rectangle</span><span style="color: #009900;">&#40;</span>loc.<span style="color: #006633;">x</span>, loc.<span style="color: #006633;">y</span>, <span style="color: #cc66cc;">200</span>, <span style="color: #cc66cc;">50</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	setBackgroundColor<span style="color: #009900;">&#40;</span><span style="color: #003399;">Activator</span>.<span style="color: #006633;">getDefault</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getColor</span><span style="color: #009900;">&#40;</span>model.<span style="color: #006633;">getColor</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	setToolTip<span style="color: #009900;">&#40;</span>createToolTip<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>运行程序，这时将鼠标移动到结点上时，就可以显示出Tooltip了，如下图：</p>
<p style="text-align:center;">
<a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图07.png" rel="lightbox[706]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图07-300x187.png" alt="" title="在图元上显示Tooltip" width="300" height="187" class="aligncenter size-medium wp-image-708" /></a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/A5E4ichzxsc" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/22/gef-step-by-step-7/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/22/gef-step-by-step-7/</feedburner:origLink></item>
		<item>
		<title>关于之前发布的gef的开发笔记</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/Vh3VNriGv2U/</link>
		<comments>http://www.zhlwish.com/2011/08/12/about-gef-step-by-step/#comments</comments>
		<pubDate>Fri, 12 Aug 2011 09:54:57 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[GEF]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=700</guid>
		<description><![CDATA[一口气发了6篇关于Eclipse GEF开发的文章，主要是记录这几天来的学习和整理所得，但是目前还没有整理完，只是涉及到在视图中显示GEF图形，到编辑器中的GEF图形编辑这个目标才完成了1/5，只怪GEF太复杂，马上会放假回家，休息一个星期再继续。]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/XUHll2YmW9UcPp8NjDRV2nYwCYI/0/da"><img src="http://feedads.g.doubleclick.net/~a/XUHll2YmW9UcPp8NjDRV2nYwCYI/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/XUHll2YmW9UcPp8NjDRV2nYwCYI/1/da"><img src="http://feedads.g.doubleclick.net/~a/XUHll2YmW9UcPp8NjDRV2nYwCYI/1/di" border="0" ismap="true"></img></a></p><p>一口气发了6篇关于Eclipse GEF开发的文章，主要是记录这几天来的学习和整理所得，但是目前还没有整理完，只是涉及到在视图中显示GEF图形，到编辑器中的GEF图形编辑这个目标才完成了1/5，只怪GEF太复杂，马上会放假回家，休息一个星期再继续。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/Vh3VNriGv2U" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/12/about-gef-step-by-step/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/12/about-gef-step-by-step/</feedburner:origLink></item>
		<item>
		<title>一步一步实现GEF – 6</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/laO1GdsWddU/</link>
		<comments>http://www.zhlwish.com/2011/08/12/gef-step-by-step-6/#comments</comments>
		<pubDate>Fri, 12 Aug 2011 09:47:14 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[GEF]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=677</guid>
		<description><![CDATA[添加连接线 要在两个结点（Node）之间显示连接线，需要在模型上添加连接线，修改showDiagram()函数，在node和node2之间添加一个Connection对象，为了方便，先在Connection类中添加connection()方法，如下所示： public void connect&#40;Node source, Node target&#41;&#123; setSource&#40;source&#41;; setTarget&#40;target&#41;; source.addOutgoingConnection&#40;this&#41;; target.addIncomingConnection&#40;this&#41;; &#125; 接着在showDiagram()方法中创建Connection模型对象，并且连接node和node2。 private void showDiagram&#40;&#41; &#123; Diagram diagram = new Diagram&#40;&#41;; &#160; Node node = new Node&#40;&#41;; node.setText&#40;&#34;测试节点&#34;&#41;; node.setLocation&#40;new Point&#40;10, 10&#41;&#41;; diagram.addNode&#40;node&#41;; &#160; Node node2 = new Node&#40;&#41;; &#8230; <a href="http://www.zhlwish.com/2011/08/12/gef-step-by-step-6/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/B0XU8EEolZB8UdnqYXAxGdkYxgg/0/da"><img src="http://feedads.g.doubleclick.net/~a/B0XU8EEolZB8UdnqYXAxGdkYxgg/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/B0XU8EEolZB8UdnqYXAxGdkYxgg/1/da"><img src="http://feedads.g.doubleclick.net/~a/B0XU8EEolZB8UdnqYXAxGdkYxgg/1/di" border="0" ismap="true"></img></a></p><p><strong>添加连接线</strong></p>
<p>要在两个结点（Node）之间显示连接线，需要在模型上添加连接线，修改showDiagram()函数，在node和node2之间添加一个Connection对象，为了方便，先在Connection类中添加connection()方法，如下所示：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> connect<span style="color: #009900;">&#40;</span>Node source, Node target<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
	setSource<span style="color: #009900;">&#40;</span>source<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	setTarget<span style="color: #009900;">&#40;</span>target<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	source.<span style="color: #006633;">addOutgoingConnection</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">this</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	target.<span style="color: #006633;">addIncomingConnection</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">this</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p><span id="more-677"></span><br />
接着在showDiagram()方法中创建Connection模型对象，并且连接node和node2。</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000066; font-weight: bold;">void</span> showDiagram<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	Diagram diagram <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Diagram<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	Node node <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Node<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node.<span style="color: #006633;">setText</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;测试节点&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node.<span style="color: #006633;">setLocation</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Point</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">10</span>, <span style="color: #cc66cc;">10</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	diagram.<span style="color: #006633;">addNode</span><span style="color: #009900;">&#40;</span>node<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	Node node2 <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Node<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node2.<span style="color: #006633;">setText</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;测试节点&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node2.<span style="color: #006633;">setLocation</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Point</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">10</span>, <span style="color: #cc66cc;">70</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	diagram.<span style="color: #006633;">addNode</span><span style="color: #009900;">&#40;</span>node2<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #003399;">Connection</span> conn <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Connection</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	conn.<span style="color: #006633;">connect</span><span style="color: #009900;">&#40;</span>node, node2<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	graphicalViewer.<span style="color: #006633;">setContents</span><span style="color: #009900;">&#40;</span>diagram<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>运行程序，但是很遗憾，连接线依然没有显示。</p>
<p><strong>显示连接线</strong></p>
<p>考虑到在<a href="一步一步实现GEF – 5">《一步一步实现GEF – 5》</a>一文中也出现过创建了模型，但是模型不显示的问题，解决办法是覆盖DiagramPart父类的getModelChildren()方法。以此类推，我们应该覆盖NodePart父类的getModelSourceConnections()和getModelTargetConnections()方法，返回Node模型的Outgoing Connections和Incoming Connections。</p>
<p>为了方便起见，我们为Node模型添加如下两个方法，分别返回Outgoing Connections和Incoming Connections。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> List<span style="color: #339933;">&lt;</span>Connection<span style="color: #339933;">&gt;</span> getIncomingConnections<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">return</span> incomings<span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> List<span style="color: #339933;">&lt;</span>Connection<span style="color: #339933;">&gt;</span> getOutgoingConnections<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">return</span> outgoings<span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>接着在NodePart类中添加如下方法：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;">@Override
<span style="color: #000000; font-weight: bold;">protected</span> List<span style="color: #339933;">&lt;</span>Connection<span style="color: #339933;">&gt;</span> getModelSourceConnections<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">return</span> <span style="color: #009900;">&#40;</span><span style="color: #009900;">&#40;</span>Node<span style="color: #009900;">&#41;</span> getModel<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getOutgoingConnections</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
@Override
<span style="color: #000000; font-weight: bold;">protected</span> List<span style="color: #339933;">&lt;</span>Connection<span style="color: #339933;">&gt;</span> getModelTargetConnections<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">return</span> <span style="color: #009900;">&#40;</span><span style="color: #009900;">&#40;</span>Node<span style="color: #009900;">&#41;</span> getModel<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getIncomingConnections</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>然后运行程序，我们可以看到，两个结点之间出现了一根细实线，也就是我们需要的连接线了。</p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图05.png" rel="lightbox[677]"><img class="aligncenter size-medium wp-image-683" title="显示两个结点之间的连接线" src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图05-300x251.png" alt="" width="300" height="251" /></a></p>
<p><strong>自定义连接线</strong></p>
<p>但是仍然有遗憾，就是连接线似乎并没有显示出箭头，或者，我们想连接线应该显示为虚线，这样又该如何实现呢？有两个方法，一是为Connection模型创建专门的Figure，二是通过覆写ConnectionPart类的父类AbstractConnectionEditPart的createFigure()方法。方便起见，我们选择第二种。</p>
<p>AbstractConnectionEditPart的createFigure()方法中创建了PolylineConnection连接线，我们直接对这个连接线进行修改。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;">@Override
<span style="color: #000000; font-weight: bold;">protected</span> IFigure createFigure<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	PolylineConnection conn <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span>PolylineConnection<span style="color: #009900;">&#41;</span> <span style="color: #000000; font-weight: bold;">super</span>.<span style="color: #006633;">createFigure</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #666666; font-style: italic;">//连接线宽度为4</span>
	conn.<span style="color: #006633;">setLineWidth</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">4</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #666666; font-style: italic;">//设置连接线为虚线，实线长度为4，空白长度为1</span>
	conn.<span style="color: #006633;">setLineDash</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #000066; font-weight: bold;">float</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#123;</span>4f,1f<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	PolylineDecoration decoration <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> PolylineDecoration<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	decoration.<span style="color: #006633;">setLineWidth</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">4</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	conn.<span style="color: #006633;">setTargetDecoration</span><span style="color: #009900;">&#40;</span>decoration<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">return</span> conn<span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>为了更好的显示出连接线的状态，我们修改NodeGefView的showDiagram()方法，将第二个结点的位置向右下移动：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;">node2.<span style="color: #006633;">setLocation</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Point</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">100</span>, <span style="color: #cc66cc;">170</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></td></tr></table></div>

<p>然后运行程序，这时候的效果图应该如下：</p>
<p style="text-align: center;">
<a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图06.png" rel="lightbox[677]"><img src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图06-300x201.png" alt="" title="自定义结点之间的连接线" width="300" height="201" class="aligncenter size-medium wp-image-686" /></a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/laO1GdsWddU" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/12/gef-step-by-step-6/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/12/gef-step-by-step-6/</feedburner:origLink></item>
		<item>
		<title>一步一步实现GEF – 5</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/1W9rxRwe8NY/</link>
		<comments>http://www.zhlwish.com/2011/08/12/gef-step-by-step/#comments</comments>
		<pubDate>Fri, 12 Aug 2011 09:45:41 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[GEF]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=662</guid>
		<description><![CDATA[显示Diagram模型 到目前为止，仅仅显示了一个节点（Node）的图形，如何显示多个节点，也就是一个Diagram的模型呢？ 我们修改NodeGefView类的showDiagram()方法，创建Diagram模型，并且创建两个Node模型，加入到Diagram中。 private void showDiagram&#40;&#41; &#123; Diagram diagram = new Diagram&#40;&#41;; &#160; Node node = new Node&#40;&#41;; node.setText&#40;&#34;测试节点&#34;&#41;; node.setLocation&#40;new Point&#40;10, 10&#41;&#41;; diagram.addNode&#40;node&#41;; &#160; Node node2 = new Node&#40;&#41;; node2.setText&#40;&#34;测试节点&#34;&#41;; node2.setLocation&#40;new Point&#40;10, 70&#41;&#41;; diagram.addNode&#40;node2&#41;; &#160; graphicalViewer.setContents&#40;diagram&#41;; &#125; 但是运行时发现，现在视图上无显示，连上一步显示的Node模型对应的矩形框都没有了。 解决这个问题，我们通过覆盖DiagramPart的父类的getModelChildren()方法实现，此方法默认返回空列表。首先在Diagram模型类中加入一个返回其孩子结点的方法： public &#8230; <a href="http://www.zhlwish.com/2011/08/12/gef-step-by-step/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/jnxACLRt5A1oc3Ara7JlN0U-ISw/0/da"><img src="http://feedads.g.doubleclick.net/~a/jnxACLRt5A1oc3Ara7JlN0U-ISw/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/jnxACLRt5A1oc3Ara7JlN0U-ISw/1/da"><img src="http://feedads.g.doubleclick.net/~a/jnxACLRt5A1oc3Ara7JlN0U-ISw/1/di" border="0" ismap="true"></img></a></p><p><strong>显示Diagram模型</strong></p>
<p>到目前为止，仅仅显示了一个节点（Node）的图形，如何显示多个节点，也就是一个Diagram的模型呢？</p>
<p>我们修改NodeGefView类的showDiagram()方法，创建Diagram模型，并且创建两个Node模型，加入到Diagram中。</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000066; font-weight: bold;">void</span> showDiagram<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	Diagram diagram <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Diagram<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	Node node <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Node<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node.<span style="color: #006633;">setText</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;测试节点&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node.<span style="color: #006633;">setLocation</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Point</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">10</span>, <span style="color: #cc66cc;">10</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	diagram.<span style="color: #006633;">addNode</span><span style="color: #009900;">&#40;</span>node<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	Node node2 <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Node<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node2.<span style="color: #006633;">setText</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;测试节点&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	node2.<span style="color: #006633;">setLocation</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Point</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">10</span>, <span style="color: #cc66cc;">70</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	diagram.<span style="color: #006633;">addNode</span><span style="color: #009900;">&#40;</span>node2<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	graphicalViewer.<span style="color: #006633;">setContents</span><span style="color: #009900;">&#40;</span>diagram<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>但是运行时发现，现在视图上无显示，连上一步显示的Node模型对应的矩形框都没有了。<br />
<span id="more-662"></span><br />
解决这个问题，我们通过覆盖DiagramPart的父类的getModelChildren()方法实现，此方法默认返回空列表。首先在Diagram模型类中加入一个返回其孩子结点的方法：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> List<span style="color: #339933;">&lt;</span>Node<span style="color: #339933;">&gt;</span> getNodes<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">return</span> nodes<span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>接着，覆盖DiagramPart的父类的getModelChildren()方法，返回Diagram模型的孩子结点。</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">@Override
<span style="color: #000000; font-weight: bold;">protected</span> <span style="color: #003399;">List</span> getModelChildren<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	Diagram diagram <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span>Diagram<span style="color: #009900;">&#41;</span>getModel<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">return</span> diagram.<span style="color: #006633;">getNodes</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>此时运行插件，看到的效果应该如下图所示：</p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图04.png" rel="lightbox[662]"><img class="size-medium wp-image-673" title="显示多个结点" src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图04-300x251.png" alt="" width="300" height="251" /></a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/1W9rxRwe8NY" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/12/gef-step-by-step/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/12/gef-step-by-step/</feedburner:origLink></item>
		<item>
		<title>一步一步实现GEF – 4</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/Y-YySYwF7hg/</link>
		<comments>http://www.zhlwish.com/2011/08/12/gef-step-by-step-4/#comments</comments>
		<pubDate>Fri, 12 Aug 2011 09:44:49 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[GEF]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=656</guid>
		<description><![CDATA[创建View 打开META-INF/MANIFEST.MF，在Extensions页面添加org.eclipse.ui.views扩展点，并添加一个名为“Nodes GEF View”的扩展点。 创建View对应的Java类 自定义视图需要继承自ViewPart类型，通过覆盖createPartControl()方法自定义视图上显示的内容。此处视图上显示一个ScrollingGraphicalViewer，GraphicViewer需要设置rootEditPart和EditPartFactory，然后调用setContent()方法传入模型对象，该方法能根据模型的类型生成相应的EditPart，然后创建相应的Figure并加入显示队列中进行绘图。 1 2 3 4 ScalableFreeformRootEditPart rootEditPart = new ScalableFreeformRootEditPart&#40;&#41;; ScrollingGraphicalViewer graphicalViewer = new ScrollingGraphicalViewer&#40;&#41;; graphicalViewer.setRootEditPart&#40;rootEditPart&#41;; graphicalViewer.setEditPartFactory&#40;new PartFactory&#40;&#41;&#41;; 整个View类的代码如下，我们自己定义了一个私有showDiagram()方法创建模型并调用setContent()方法。 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 &#8230; <a href="http://www.zhlwish.com/2011/08/12/gef-step-by-step-4/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/38OvGAVNq9QMbZ003JBI36kgGg8/0/da"><img src="http://feedads.g.doubleclick.net/~a/38OvGAVNq9QMbZ003JBI36kgGg8/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/38OvGAVNq9QMbZ003JBI36kgGg8/1/da"><img src="http://feedads.g.doubleclick.net/~a/38OvGAVNq9QMbZ003JBI36kgGg8/1/di" border="0" ismap="true"></img></a></p><p><strong>创建View</strong></p>
<p>打开META-INF/MANIFEST.MF，在Extensions页面添加org.eclipse.ui.views扩展点，并添加一个名为“Nodes GEF View”的扩展点。</p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图01.png" rel="lightbox[656]"><img class="size-medium wp-image-631 aligncenter" title="创建View" src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图01-300x134.png" alt="" width="300" height="134" /></a></p>
<p><strong>创建View对应的Java类</strong></p>
<p>自定义视图需要继承自ViewPart类型，通过覆盖createPartControl()方法自定义视图上显示的内容。此处视图上显示一个ScrollingGraphicalViewer，GraphicViewer需要设置rootEditPart和EditPartFactory，然后调用setContent()方法传入模型对象，该方法能根据模型的类型生成相应的EditPart，然后创建相应的Figure并加入显示队列中进行绘图。<br />
<span id="more-656"></span></p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;">ScalableFreeformRootEditPart rootEditPart <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ScalableFreeformRootEditPart<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
ScrollingGraphicalViewer graphicalViewer <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ScrollingGraphicalViewer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
graphicalViewer.<span style="color: #006633;">setRootEditPart</span><span style="color: #009900;">&#40;</span>rootEditPart<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
graphicalViewer.<span style="color: #006633;">setEditPartFactory</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> PartFactory<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></td></tr></table></div>

<p>整个View类的代码如下，我们自己定义了一个私有showDiagram()方法创建模型并调用setContent()方法。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.view</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.draw2d.geometry.Point</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.gef.editparts.ScalableFreeformRootEditPart</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.gef.ui.parts.ScrollingGraphicalViewer</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.swt.graphics.Color</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.swt.graphics.RGB</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.swt.widgets.Composite</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.ui.part.ViewPart</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.Activator</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.model.Node</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.part.PartFactory</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> NodeGefView <span style="color: #000000; font-weight: bold;">extends</span> ViewPart <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">Color</span> COLOR_WHITE <span style="color: #339933;">=</span> <span style="color: #003399;">Activator</span>.<span style="color: #006633;">getDefault</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getColor</span><span style="color: #009900;">&#40;</span>
			<span style="color: #000000; font-weight: bold;">new</span> RGB<span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">255</span>, <span style="color: #cc66cc;">255</span>, <span style="color: #cc66cc;">255</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> ScrollingGraphicalViewer graphicalViewer<span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> NodeGefView<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">super</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> createPartControl<span style="color: #009900;">&#40;</span><span style="color: #003399;">Composite</span> parent<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		ScalableFreeformRootEditPart rootEditPart <span style="color: #339933;">=</span> 
				<span style="color: #000000; font-weight: bold;">new</span> ScalableFreeformRootEditPart<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		graphicalViewer <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ScrollingGraphicalViewer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		graphicalViewer.<span style="color: #006633;">createControl</span><span style="color: #009900;">&#40;</span>parent<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		graphicalViewer.<span style="color: #006633;">getControl</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">setBackground</span><span style="color: #009900;">&#40;</span>COLOR_WHITE<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		graphicalViewer.<span style="color: #006633;">setRootEditPart</span><span style="color: #009900;">&#40;</span>rootEditPart<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		graphicalViewer.<span style="color: #006633;">setEditPartFactory</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> PartFactory<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
		showDiagram<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setFocus<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		graphicalViewer.<span style="color: #006633;">getControl</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">setFocus</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000066; font-weight: bold;">void</span> showDiagram<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		Node node <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Node<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		node.<span style="color: #006633;">setText</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;测试节点&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		node.<span style="color: #006633;">setLocation</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Point</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">10</span>, <span style="color: #cc66cc;">10</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
		graphicalViewer.<span style="color: #006633;">setContents</span><span style="color: #009900;">&#40;</span>node<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>运行此插件，点击菜单Window-&gt;Show View-&gt;Others，找到Other节点，展开后点击“Nodes GEF View”视图，打开后，可以看到节点显示在了视图上。</p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图03.png" rel="lightbox[656]"><img class="size-medium wp-image-657 aligncenter" title="GEF图形显示在了视图上" src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图03-300x251.png" alt="" width="300" height="251" /></a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/Y-YySYwF7hg" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/12/gef-step-by-step-4/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/12/gef-step-by-step-4/</feedburner:origLink></item>
		<item>
		<title>一步一步实现GEF – 3</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/RbzU3lOjigM/</link>
		<comments>http://www.zhlwish.com/2011/08/12/gef-step-by-step-3/#comments</comments>
		<pubDate>Fri, 12 Aug 2011 09:43:52 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[GEF]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=652</guid>
		<description><![CDATA[实现模型对应的Part 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 package com.zhlwish.learngef.part; &#160; import org.eclipse.draw2d.IFigure; import org.eclipse.gef.editparts.AbstractGraphicalEditPart; &#160; import com.zhlwish.learngef.figure.NodeFigure; import com.zhlwish.learngef.model.Node; &#160; public class NodePart extends AbstractGraphicalEditPart&#123; &#160; &#8230; <a href="http://www.zhlwish.com/2011/08/12/gef-step-by-step-3/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/R5CDD1OZa8sOLHpG8eICzdnGwcY/0/da"><img src="http://feedads.g.doubleclick.net/~a/R5CDD1OZa8sOLHpG8eICzdnGwcY/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/R5CDD1OZa8sOLHpG8eICzdnGwcY/1/da"><img src="http://feedads.g.doubleclick.net/~a/R5CDD1OZa8sOLHpG8eICzdnGwcY/1/di" border="0" ismap="true"></img></a></p><p><strong>实现模型对应的Part</strong></p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.part</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.draw2d.IFigure</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.gef.editparts.AbstractGraphicalEditPart</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.figure.NodeFigure</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.model.Node</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> NodePart <span style="color: #000000; font-weight: bold;">extends</span> AbstractGraphicalEditPart<span style="color: #009900;">&#123;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">protected</span> IFigure createFigure<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> <span style="color: #000000; font-weight: bold;">new</span> NodeFigure<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#40;</span>Node<span style="color: #009900;">&#41;</span> getModel<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">protected</span> <span style="color: #000066; font-weight: bold;">void</span> createEditPolicies<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p><span id="more-652"></span></p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.part</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.gef.editparts.AbstractConnectionEditPart</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> ConnectionPart <span style="color: #000000; font-weight: bold;">extends</span> AbstractConnectionEditPart<span style="color: #009900;">&#123;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">protected</span> <span style="color: #000066; font-weight: bold;">void</span> createEditPolicies<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>


<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.part</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.draw2d.IFigure</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.gef.editparts.AbstractGraphicalEditPart</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.figure.DiagramFigure</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> DiagramPart <span style="color: #000000; font-weight: bold;">extends</span> AbstractGraphicalEditPart <span style="color: #009900;">&#123;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">protected</span> IFigure createFigure<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> <span style="color: #000000; font-weight: bold;">new</span> DiagramFigure<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">protected</span> <span style="color: #000066; font-weight: bold;">void</span> createEditPolicies<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p><strong>实现根据模型的类型创建相应的EditPart的工厂</strong></p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.part</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.gef.EditPart</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.gef.EditPartFactory</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.model.Connection</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.model.Diagram</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.model.Node</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> PartFactory <span style="color: #000000; font-weight: bold;">implements</span> EditPartFactory<span style="color: #009900;">&#123;</span>
&nbsp;
	@Override
	<span style="color: #000000; font-weight: bold;">public</span> EditPart createEditPart<span style="color: #009900;">&#40;</span>EditPart context, <span style="color: #003399;">Object</span> model<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		EditPart part <span style="color: #339933;">=</span> <span style="color: #000066; font-weight: bold;">null</span><span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>model <span style="color: #000000; font-weight: bold;">instanceof</span> Node<span style="color: #009900;">&#41;</span>
			part <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> NodePart<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>model <span style="color: #000000; font-weight: bold;">instanceof</span> <span style="color: #003399;">Connection</span><span style="color: #009900;">&#41;</span>
			part <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ConnectionPart<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>model <span style="color: #000000; font-weight: bold;">instanceof</span> Diagram<span style="color: #009900;">&#41;</span>
			part <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> DiagramPart<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>part <span style="color: #339933;">!=</span> <span style="color: #000066; font-weight: bold;">null</span><span style="color: #009900;">&#41;</span>
			part.<span style="color: #006633;">setModel</span><span style="color: #009900;">&#40;</span>model<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">return</span> part<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/RbzU3lOjigM" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/12/gef-step-by-step-3/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/12/gef-step-by-step-3/</feedburner:origLink></item>
		<item>
		<title>一步一步实现GEF – 2</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/5DYJbBbYhwY/</link>
		<comments>http://www.zhlwish.com/2011/08/12/gef-step-by-step-2/#comments</comments>
		<pubDate>Fri, 12 Aug 2011 09:42:37 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[GEF]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=642</guid>
		<description><![CDATA[创建模型对应的Figure 由于节点对应的Figure中需要使用Color，因此先在Activator类中加入ColorRegistry类型的属性，修改之后如下，其中第20行和第50行以后为新增加的。 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 &#8230; <a href="http://www.zhlwish.com/2011/08/12/gef-step-by-step-2/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/P3jEFafpTrr8nf17FF0YC4lYgqc/0/da"><img src="http://feedads.g.doubleclick.net/~a/P3jEFafpTrr8nf17FF0YC4lYgqc/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/P3jEFafpTrr8nf17FF0YC4lYgqc/1/da"><img src="http://feedads.g.doubleclick.net/~a/P3jEFafpTrr8nf17FF0YC4lYgqc/1/di" border="0" ismap="true"></img></a></p><p><strong>创建模型对应的Figure</strong></p>
<p>由于节点对应的Figure中需要使用Color，因此先在Activator类中加入ColorRegistry类型的属性，修改之后如下，其中第20行和第50行以后为新增加的。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.jface.resource.ColorRegistry</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.swt.graphics.Color</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.swt.graphics.RGB</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.ui.plugin.AbstractUIPlugin</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.osgi.framework.BundleContext</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #008000; font-style: italic; font-weight: bold;">/**
 * The activator class controls the plug-in life cycle
 */</span>
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> <span style="color: #003399;">Activator</span> <span style="color: #000000; font-weight: bold;">extends</span> AbstractUIPlugin <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #666666; font-style: italic;">// The plug-in ID</span>
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000000; font-weight: bold;">final</span> <span style="color: #003399;">String</span> PLUGIN_ID <span style="color: #339933;">=</span> <span style="color: #0000ff;">&quot;com.zhlwish.learngef&quot;</span><span style="color: #339933;">;</span> <span style="color: #666666; font-style: italic;">//$NON-NLS-1$</span>
&nbsp;
	<span style="color: #666666; font-style: italic;">// The shared instance</span>
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">Activator</span> plugin<span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> ColorRegistry colorRegistry <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ColorRegistry<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #008000; font-style: italic; font-weight: bold;">/**
	 * The constructor
	 */</span>
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">Activator</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #666666; font-style: italic;">/*
	 * (non-Javadoc)
	 * @see org.eclipse.ui.plugin.AbstractUIPlugin#start(org.osgi.framework.BundleContext)
	 */</span>
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> start<span style="color: #009900;">&#40;</span>BundleContext context<span style="color: #009900;">&#41;</span> <span style="color: #000000; font-weight: bold;">throws</span> <span style="color: #003399;">Exception</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">super</span>.<span style="color: #006633;">start</span><span style="color: #009900;">&#40;</span>context<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		plugin <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">this</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #666666; font-style: italic;">/*
	 * (non-Javadoc)
	 * @see org.eclipse.ui.plugin.AbstractUIPlugin#stop(org.osgi.framework.BundleContext)
	 */</span>
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> stop<span style="color: #009900;">&#40;</span>BundleContext context<span style="color: #009900;">&#41;</span> <span style="color: #000000; font-weight: bold;">throws</span> <span style="color: #003399;">Exception</span> <span style="color: #009900;">&#123;</span>
		plugin <span style="color: #339933;">=</span> <span style="color: #000066; font-weight: bold;">null</span><span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">super</span>.<span style="color: #006633;">stop</span><span style="color: #009900;">&#40;</span>context<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #008000; font-style: italic; font-weight: bold;">/**
	 * Returns the shared instance
	 *
	 * @return the shared instance
	 */</span>
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">Activator</span> getDefault<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> plugin<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">Color</span> getColor<span style="color: #009900;">&#40;</span>RGB rgb<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		<span style="color: #003399;">Color</span> color <span style="color: #339933;">=</span> colorRegistry.<span style="color: #006633;">get</span><span style="color: #009900;">&#40;</span>rgb.<span style="color: #006633;">toString</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>color <span style="color: #339933;">==</span> <span style="color: #000066; font-weight: bold;">null</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
			colorRegistry.<span style="color: #006633;">put</span><span style="color: #009900;">&#40;</span>rgb.<span style="color: #006633;">toString</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>, rgb<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
		color <span style="color: #339933;">=</span> colorRegistry.<span style="color: #006633;">get</span><span style="color: #009900;">&#40;</span>rgb.<span style="color: #006633;">toString</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">return</span> color<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p><span id="more-642"></span><br />
GEF严格遵循MVC架构实现，Figure是模型对应的图形，由于Diagram对应整个GEF图形，因此继承FreeformLayer</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.figure</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.draw2d.FreeformLayer</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.draw2d.FreeformLayout</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> DiagramFigure <span style="color: #000000; font-weight: bold;">extends</span> FreeformLayer<span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> DiagramFigure<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">setLayoutManager</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> FreeformLayout<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>Node类代表一个节点，我们用矩形框内嵌入文本显示，因此NodeFigure继承自RectangleFigure，同时使用setBounds()方法将Label的大小和位置设为和矩形框一致，这样文本就会在中间显示。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.figure</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.draw2d.Label</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.draw2d.RectangleFigure</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.draw2d.geometry.Point</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.draw2d.geometry.Rectangle</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.swt.graphics.RGB</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.Activator</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">com.zhlwish.learngef.model.Node</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> NodeFigure <span style="color: #000000; font-weight: bold;">extends</span> RectangleFigure <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> Node model<span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">Label</span> label<span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> NodeFigure<span style="color: #009900;">&#40;</span>Node node<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		model <span style="color: #339933;">=</span> node<span style="color: #339933;">;</span>
&nbsp;
		label <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Label</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		label.<span style="color: #006633;">setText</span><span style="color: #009900;">&#40;</span>model.<span style="color: #006633;">getText</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		label.<span style="color: #006633;">setForegroundColor</span><span style="color: #009900;">&#40;</span><span style="color: #003399;">Activator</span>.<span style="color: #006633;">getDefault</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getColor</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> RGB<span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">0</span>, <span style="color: #cc66cc;">0</span>, <span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		add<span style="color: #009900;">&#40;</span>label<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
		<span style="color: #666666; font-style: italic;">//通过模型获得位置</span>
		<span style="color: #003399;">Point</span> loc <span style="color: #339933;">=</span> model.<span style="color: #006633;">getLocation</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		setBounds<span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Rectangle</span><span style="color: #009900;">&#40;</span>loc.<span style="color: #006633;">x</span>, loc.<span style="color: #006633;">y</span>, <span style="color: #cc66cc;">200</span>, <span style="color: #cc66cc;">50</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		setBackgroundColor<span style="color: #009900;">&#40;</span><span style="color: #003399;">Activator</span>.<span style="color: #006633;">getDefault</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getColor</span><span style="color: #009900;">&#40;</span>model.<span style="color: #006633;">getColor</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setBounds<span style="color: #009900;">&#40;</span><span style="color: #003399;">Rectangle</span> rect<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">super</span>.<span style="color: #006633;">setBounds</span><span style="color: #009900;">&#40;</span>rect<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">label</span>.<span style="color: #006633;">setBounds</span><span style="color: #009900;">&#40;</span>rect<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>由于Connection代表的是连接线对象，为简单的折线，此处不专门为其指定专门的Figure。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/5DYJbBbYhwY" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/12/gef-step-by-step-2/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/12/gef-step-by-step-2/</feedburner:origLink></item>
		<item>
		<title>一步一步实现GEF – 1</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/5W33BJLc0q4/</link>
		<comments>http://www.zhlwish.com/2011/08/12/gef-step-by-step-1/#comments</comments>
		<pubDate>Fri, 12 Aug 2011 09:40:55 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[GEF]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=628</guid>
		<description><![CDATA[创建项目 创建Eclipse Plugin项目，名称为com.zhlwish.learngef 打开META-INF/ MANIFEST.MF，在Dependencies标签页上Required Plug-ins区域，添加名称为org.eclipse.gef的插件依赖。 创建模型 定义三个模型类，Diagram，Node，Connection，分别代表整个GEF图，节点，节点之间的连线，GEF图类由结点组成 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 &#8230; <a href="http://www.zhlwish.com/2011/08/12/gef-step-by-step-1/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/thZytzfDR9IdzZzOoYjPuh9xZpw/0/da"><img src="http://feedads.g.doubleclick.net/~a/thZytzfDR9IdzZzOoYjPuh9xZpw/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/thZytzfDR9IdzZzOoYjPuh9xZpw/1/da"><img src="http://feedads.g.doubleclick.net/~a/thZytzfDR9IdzZzOoYjPuh9xZpw/1/di" border="0" ismap="true"></img></a></p><p><strong>创建项目</strong></p>
<p>创建Eclipse Plugin项目，名称为com.zhlwish.learngef</p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图00.png" rel="lightbox[628]"><img class="size-medium wp-image-630 aligncenter" title="创建Eclipse Plugin项目" src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图00-277x300.png" alt="" width="277" height="300" /></a></p>
<p>打开META-INF/ MANIFEST.MF，在Dependencies标签页上Required Plug-ins区域，添加名称为org.eclipse.gef的插件依赖。</p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/截图02.png" rel="lightbox[628]"><img class="size-medium wp-image-629 aligncenter" title="添加org.eclipse.gef插件依赖" src="http://www.zhlwish.com/wp-content/uploads/2011/08/截图02-300x183.png" alt="" width="300" height="183" /></a></p>
<p><span id="more-628"></span><br />
<strong>创建模型</strong></p>
<p>定义三个模型类，Diagram，Node，Connection，分别代表整个GEF图，节点，节点之间的连线，GEF图类由结点组成</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.model</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.util.ArrayList</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.util.List</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.draw2d.geometry.Point</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.swt.graphics.RGB</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> Node <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">String</span> text <span style="color: #339933;">=</span> <span style="color: #0000ff;">&quot;&quot;</span><span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">private</span> RGB color <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> RGB<span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">120</span>, <span style="color: #cc66cc;">120</span>, <span style="color: #cc66cc;">120</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">Point</span> location <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Point</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">0</span>, <span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> List<span style="color: #339933;">&lt;</span>Connection<span style="color: #339933;">&gt;</span> incomings <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ArrayList<span style="color: #339933;">&lt;</span>Connection<span style="color: #339933;">&gt;</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">private</span> List<span style="color: #339933;">&lt;</span>Connection<span style="color: #339933;">&gt;</span> outgoings <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ArrayList<span style="color: #339933;">&lt;</span>Connection<span style="color: #339933;">&gt;</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">String</span> getText<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> text<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setText<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> text<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">text</span> <span style="color: #339933;">=</span> text<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> RGB getColor<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> color<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setColor<span style="color: #009900;">&#40;</span>RGB color<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">color</span> <span style="color: #339933;">=</span> color<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">Point</span> getLocation<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> location<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setLocation<span style="color: #009900;">&#40;</span><span style="color: #003399;">Point</span> location<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">location</span> <span style="color: #339933;">=</span> location<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> addIncomingConnection<span style="color: #009900;">&#40;</span><span style="color: #003399;">Connection</span> conn<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		incomings.<span style="color: #006633;">add</span><span style="color: #009900;">&#40;</span>conn<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> rmIncomingConnection<span style="color: #009900;">&#40;</span><span style="color: #003399;">Connection</span> conn<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		incomings.<span style="color: #006633;">remove</span><span style="color: #009900;">&#40;</span>conn<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> addOutgoingConnection<span style="color: #009900;">&#40;</span><span style="color: #003399;">Connection</span> conn<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		outgoings.<span style="color: #006633;">add</span><span style="color: #009900;">&#40;</span>conn<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> rmOutgoingConnection<span style="color: #009900;">&#40;</span><span style="color: #003399;">Connection</span> conn<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		outgoings.<span style="color: #006633;">remove</span><span style="color: #009900;">&#40;</span>conn<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>


<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.model</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> <span style="color: #003399;">Connection</span> <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> Node source<span style="color: #339933;">;</span>
	<span style="color: #000000; font-weight: bold;">private</span> Node target<span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> Node getSource<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> source<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setSource<span style="color: #009900;">&#40;</span>Node source<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">source</span> <span style="color: #339933;">=</span> source<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> Node getTarget<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> target<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> setTarget<span style="color: #009900;">&#40;</span>Node target<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">target</span> <span style="color: #339933;">=</span> target<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>


<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.learngef.model</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.util.ArrayList</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.util.List</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> Diagram <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">List</span> nodes <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">ArrayList</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> addNode<span style="color: #009900;">&#40;</span>Node node<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		nodes.<span style="color: #006633;">add</span><span style="color: #009900;">&#40;</span>node<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> rmNode<span style="color: #009900;">&#40;</span>Node node<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
		nodes.<span style="color: #006633;">remove</span><span style="color: #009900;">&#40;</span>node<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/5W33BJLc0q4" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/12/gef-step-by-step-1/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/12/gef-step-by-step-1/</feedburner:origLink></item>
		<item>
		<title>Java实践：最好提供无参数的构造函数</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/dGDRqZcxBuw/</link>
		<comments>http://www.zhlwish.com/2011/08/11/provide-none-param-constructor-in-java/#comments</comments>
		<pubDate>Thu, 11 Aug 2011 08:02:06 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Java]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=605</guid>
		<description><![CDATA[一个类在没有显式定义构造函数的时候，Java会隐式提供一个无参数的构造函数。但是当显式定义了构造函数的情况下，Java就不会提供这个无参数的构造函数了。这是由于在显式定义的构造函数中可能进行了一些必要的初始化工作，此时如果错误调用默认无参构造函数会导致这些必须的初始化工作并没有完成，进而导致程序异常。 经过编程实践，本人认为还是有必要再显式定义了有参构造函数的情况下，仍然显式定义一个无参构造函数。主要原因是“最好提供缺省值”（It will be better to provide a default value），另外一个原因则是在工厂方法中大量使用的java.lang.Class.newInstance()方法只能调用无参构造函数。 提供缺省值 在定义类的时候，最好为属性设置缺省值，以免出现Java中最常见的NullPointException，如下所示，当然此代码并不涉及构造函数神马事情，此处省略不相关的部分，下文类似。 1 2 3 public class NodeEditPart&#123; private List&#60;Connection&#62; incomings = new ArrayList&#60;Connection&#62;&#40;0&#41;; &#125; 通过构造函数设置属性值是非常常见的。下面代码摘取自java.awt.Label类，其中定义了空的构造函数，并且设置文本默认为空字符串。 1 2 3 4 5 6 7 8 9 10 public Label&#40;&#41; &#123; this&#40;&#34;&#34;, &#8230; <a href="http://www.zhlwish.com/2011/08/11/provide-none-param-constructor-in-java/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/1Xpmkqn-wknXX1ZZ_DH319sNS-A/0/da"><img src="http://feedads.g.doubleclick.net/~a/1Xpmkqn-wknXX1ZZ_DH319sNS-A/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/1Xpmkqn-wknXX1ZZ_DH319sNS-A/1/da"><img src="http://feedads.g.doubleclick.net/~a/1Xpmkqn-wknXX1ZZ_DH319sNS-A/1/di" border="0" ismap="true"></img></a></p><p>一个类在没有显式定义构造函数的时候，Java会隐式提供一个无参数的构造函数。但是当显式定义了构造函数的情况下，Java就不会提供这个无参数的构造函数了。这是由于在显式定义的构造函数中可能进行了一些必要的初始化工作，此时如果错误调用默认无参构造函数会导致这些必须的初始化工作并没有完成，进而导致程序异常。</p>
<p>经过编程实践，本人认为还是有必要再显式定义了有参构造函数的情况下，仍然显式定义一个无参构造函数。主要原因是“最好提供缺省值”（It will be better to provide a default value），另外一个原因则是在工厂方法中大量使用的java.lang.Class.newInstance()方法只能调用无参构造函数。<br />
<span id="more-605"></span></p>
<p><strong>提供缺省值</strong><br />
在定义类的时候，最好为属性设置缺省值，以免出现Java中最常见的NullPointException，如下所示，当然此代码并不涉及构造函数神马事情，此处省略不相关的部分，下文类似。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> NodeEditPart<span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">private</span> List<span style="color: #339933;">&lt;</span>Connection<span style="color: #339933;">&gt;</span> incomings <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ArrayList<span style="color: #339933;">&lt;</span>Connection<span style="color: #339933;">&gt;</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>通过构造函数设置属性值是非常常见的。下面代码摘取自java.awt.Label类，其中定义了空的构造函数，并且设置文本默认为空字符串。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">Label</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">this</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;&quot;</span>, LEFT<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">Label</span><span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> text<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">this</span><span style="color: #009900;">&#40;</span>text, LEFT<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">Label</span><span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> text, <span style="color: #000066; font-weight: bold;">int</span> alignment<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">text</span> <span style="color: #339933;">=</span> text<span style="color: #339933;">;</span>
	setAlignment<span style="color: #009900;">&#40;</span>alignment<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p><strong>用newInstance()方法创建对象</strong><br />
下面代码定义了ElementFactory工厂类，通过构造函数传入类型对象(java.lang.Class)，然后调用newInstance()创建对象。由于newInstance()只能调用无参构造函数，因此如果类不定义无参构造函数，则无法使用此方法进行创建，这也是此方法不安全的原因所在。当然如果必要的话，也可以使用反射的方式调用有参构造函数，只是相应比较复杂。</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">class</span> ElementFactory <span style="color: #009900;">&#123;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">Object</span> template<span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> ElementFactory<span style="color: #009900;">&#40;</span><span style="color: #003399;">Object</span> template<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">template</span> <span style="color: #339933;">=</span> template<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">Object</span> getNewObject<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">try</span> <span style="color: #009900;">&#123;</span>
			<span style="color: #000000; font-weight: bold;">return</span> <span style="color: #009900;">&#40;</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">Class</span><span style="color: #009900;">&#41;</span> template<span style="color: #009900;">&#41;</span>.<span style="color: #006633;">newInstance</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span> <span style="color: #000000; font-weight: bold;">catch</span> <span style="color: #009900;">&#40;</span><span style="color: #003399;">Exception</span> e<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
			e.<span style="color: #006633;">printStackTrace</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
			<span style="color: #000000; font-weight: bold;">return</span> <span style="color: #000066; font-weight: bold;">null</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #003399;">Object</span> getObjectType<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000000; font-weight: bold;">return</span> template<span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></td></tr></table></div>

<p>客户端使用此方法的时候如下，如果Label不定义无参构造函数，则会抛出异常：</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
</pre></td><td class="code"><pre class="java" style="font-family:Verdana,Courier New;">ElementFactory factory <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ElementFactory<span style="color: #009900;">&#40;</span><span style="color: #003399;">Label</span>.<span style="color: #000000; font-weight: bold;">class</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #003399;">Label</span> label <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span><span style="color: #003399;">Label</span><span style="color: #009900;">&#41;</span> factory.<span style="color: #006633;">getNewObject</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></td></tr></table></div>

<p><strong>总结</strong><br />
以上只是本人在开发过程中的一点心得，也是避免发生运行时异常的一种好的编程习惯，如果不对，敬请指正。</p>
<p><strong>参考</strong></p>
<p><a title="Using Java Reflection" href="http://java.sun.com/developer/technicalArticles/ALT/Reflection/" target="_blank">Using Java Reflection</a><br />
<a href="http://java.e800.com.cn/articles/2008/411/1207863273344940094_1.html" target="_blank">Java关键字new和newInstance的区别方法</a></p>
<p><strong>版权</strong><br />
本文是本博客原创文章，您可以自由转载，但转载请注明来源。</p>
<p>< 全文完></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/dGDRqZcxBuw" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/11/provide-none-param-constructor-in-java/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/11/provide-none-param-constructor-in-java/</feedburner:origLink></item>
		<item>
		<title>[恶搞配音] 还珠格格新白娘子传奇——经典尼玛伤不起</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/XNgEuhtViXA/</link>
		<comments>http://www.zhlwish.com/2011/08/10/1/#comments</comments>
		<pubDate>Wed, 10 Aug 2011 13:14:19 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=599</guid>
		<description><![CDATA[白娘子的配音太像了： http://v.youku.com/v_show/id_XMjg5ODMwMjQ4.html]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/CEjSQiiGLZMBfvfLHjOQLwHiyT4/0/da"><img src="http://feedads.g.doubleclick.net/~a/CEjSQiiGLZMBfvfLHjOQLwHiyT4/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/CEjSQiiGLZMBfvfLHjOQLwHiyT4/1/da"><img src="http://feedads.g.doubleclick.net/~a/CEjSQiiGLZMBfvfLHjOQLwHiyT4/1/di" border="0" ismap="true"></img></a></p><p>白娘子的配音太像了：<br />
<a href="http://v.youku.com/v_show/id_XMjg5ODMwMjQ4.html">http://v.youku.com/v_show/id_XMjg5ODMwMjQ4.html</a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/XNgEuhtViXA" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/10/1/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/10/1/</feedburner:origLink></item>
		<item>
		<title>老美喝酒的习惯哪儿来的?</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/a2vBkxaHuaQ/</link>
		<comments>http://www.zhlwish.com/2011/08/10/593/#comments</comments>
		<pubDate>Wed, 10 Aug 2011 01:30:10 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=593</guid>
		<description><![CDATA[为什么老美喜欢有事儿没事儿都拿点酒出来喝呢，不管是在办公室还是在家里，而且好像吃饭的时候都不喝酒，这种风俗来自于哪儿？截图来自于《State.of.Play》]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/vVUwWTLuATEpIOI9kYpX3rorsq4/0/da"><img src="http://feedads.g.doubleclick.net/~a/vVUwWTLuATEpIOI9kYpX3rorsq4/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/vVUwWTLuATEpIOI9kYpX3rorsq4/1/da"><img src="http://feedads.g.doubleclick.net/~a/vVUwWTLuATEpIOI9kYpX3rorsq4/1/di" border="0" ismap="true"></img></a></p><p>为什么老美喜欢有事儿没事儿都拿点酒出来喝呢，不管是在办公室还是在家里，而且好像吃饭的时候都不喝酒，这种风俗来自于哪儿？截图来自于《State.of.Play》</p>
<p><img class="alignnone size-medium wp-image-594" title="State.of.Play" src="http://www.zhlwish.com/wp-content/uploads/2011/08/State.of_.Play_-300x127.jpg" alt="" width="300" height="127" /></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/a2vBkxaHuaQ" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/10/593/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/10/593/</feedburner:origLink></item>
		<item>
		<title>Google Music beta初体验</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/RwLUDiC_hpA/</link>
		<comments>http://www.zhlwish.com/2011/08/09/google-music-beta-exp/#comments</comments>
		<pubDate>Mon, 08 Aug 2011 16:27:12 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=587</guid>
		<description><![CDATA[Google Music绝对是虾米这样的网站的克星，本地上传+云存储+在线播放+Android云同步，如果只是提供给用户存储的空间而不传播，应该不会有版权问题吧。我有4个邀请码。http://music.google.com/]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/TgSlLglJFSlN0KYwwEtcVCOHGIY/0/da"><img src="http://feedads.g.doubleclick.net/~a/TgSlLglJFSlN0KYwwEtcVCOHGIY/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/TgSlLglJFSlN0KYwwEtcVCOHGIY/1/da"><img src="http://feedads.g.doubleclick.net/~a/TgSlLglJFSlN0KYwwEtcVCOHGIY/1/di" border="0" ismap="true"></img></a></p><p>Google Music绝对是虾米这样的网站的克星，本地上传+云存储+在线播放+Android云同步，如果只是提供给用户存储的空间而不传播，应该不会有版权问题吧。我有4个邀请码。<a href="http://music.google.com/">http://music.google.com/</a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/RwLUDiC_hpA" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/09/google-music-beta-exp/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/09/google-music-beta-exp/</feedburner:origLink></item>
		<item>
		<title>计划看建党伟业</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/Y8JTtionGaY/</link>
		<comments>http://www.zhlwish.com/2011/08/08/581/#comments</comments>
		<pubDate>Mon, 08 Aug 2011 15:28:05 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=581</guid>
		<description><![CDATA[我准备把《建党伟业》下到电脑上看一下，看看历史是如何被捏造，被美化。或者我本不应该以历史的角度去看待这部献礼的“电影”。]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/4SDHJc5b9sEcRJzOB3TsMnAG5AI/0/da"><img src="http://feedads.g.doubleclick.net/~a/4SDHJc5b9sEcRJzOB3TsMnAG5AI/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/4SDHJc5b9sEcRJzOB3TsMnAG5AI/1/da"><img src="http://feedads.g.doubleclick.net/~a/4SDHJc5b9sEcRJzOB3TsMnAG5AI/1/di" border="0" ismap="true"></img></a></p><p>我准备把《建党伟业》下到电脑上看一下，看看历史是如何被捏造，被美化。或者我本不应该以历史的角度去看待这部献礼的“电影”。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/Y8JTtionGaY" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/08/581/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/08/581/</feedburner:origLink></item>
		<item>
		<title>交流的关键是如果能抓住双方的关注点</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/AgHRbvvjP6M/</link>
		<comments>http://www.zhlwish.com/2011/08/08/point-on-communicatio/#comments</comments>
		<pubDate>Mon, 08 Aug 2011 08:11:09 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=578</guid>
		<description><![CDATA[ok，又不是专门的技术讲座，没有必要讲这么清楚的吧，而且别人公司的关注点并不在于图像的识别技术嘛。]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/QD_O9mPEryFZn0poktdigAmUvys/0/da"><img src="http://feedads.g.doubleclick.net/~a/QD_O9mPEryFZn0poktdigAmUvys/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/QD_O9mPEryFZn0poktdigAmUvys/1/da"><img src="http://feedads.g.doubleclick.net/~a/QD_O9mPEryFZn0poktdigAmUvys/1/di" border="0" ismap="true"></img></a></p><p>ok，又不是专门的技术讲座，没有必要讲这么清楚的吧，而且别人公司的关注点并不在于图像的识别技术嘛。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/AgHRbvvjP6M" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/08/point-on-communicatio/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/08/point-on-communicatio/</feedburner:origLink></item>
		<item>
		<title>WordPress主题：mistylook</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/yuE1XrgYZ1g/</link>
		<comments>http://www.zhlwish.com/2011/08/08/wordpress-theme-mistylook/#comments</comments>
		<pubDate>Mon, 08 Aug 2011 07:58:58 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=576</guid>
		<description><![CDATA[非常漂亮简洁的主题，不像suffusion那么复杂，至少对我来讲suffusion太复杂了，链接地址：http://wpthemes.info/misty-look/]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/gRKISwDM9ALCIcY9Wu7O4ONs8Rw/0/da"><img src="http://feedads.g.doubleclick.net/~a/gRKISwDM9ALCIcY9Wu7O4ONs8Rw/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/gRKISwDM9ALCIcY9Wu7O4ONs8Rw/1/da"><img src="http://feedads.g.doubleclick.net/~a/gRKISwDM9ALCIcY9Wu7O4ONs8Rw/1/di" border="0" ismap="true"></img></a></p><p>非常漂亮简洁的主题，不像suffusion那么复杂，至少对我来讲suffusion太复杂了，链接地址：<a href="http://wpthemes.info/misty-look/" target="_blank">http://wpthemes.info/misty-look/</a></p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/yuE1XrgYZ1g" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/08/wordpress-theme-mistylook/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/08/wordpress-theme-mistylook/</feedburner:origLink></item>
		<item>
		<title>aside的效果</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/ekaYdurBvgg/</link>
		<comments>http://www.zhlwish.com/2011/08/08/572/#comments</comments>
		<pubDate>Mon, 08 Aug 2011 07:54:11 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=572</guid>
		<description><![CDATA[早就听说wordpress开始支持aside了，没尝试过，现在试一下效果]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/BWipvAF-IM57tfCL6QhHM5omIfw/0/da"><img src="http://feedads.g.doubleclick.net/~a/BWipvAF-IM57tfCL6QhHM5omIfw/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/BWipvAF-IM57tfCL6QhHM5omIfw/1/da"><img src="http://feedads.g.doubleclick.net/~a/BWipvAF-IM57tfCL6QhHM5omIfw/1/di" border="0" ismap="true"></img></a></p><p>早就听说wordpress开始支持aside了，没尝试过，现在试一下效果</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/ekaYdurBvgg" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/08/572/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/08/572/</feedburner:origLink></item>
		<item>
		<title>JFace中的GridLayoutFactory和GridDataFactory</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/7O1JhqEKNKs/</link>
		<comments>http://www.zhlwish.com/2011/08/05/jface_gridlayoutfactory_griddatafactory/#comments</comments>
		<pubDate>Fri, 05 Aug 2011 08:08:01 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[rcp]]></category>
		<category><![CDATA[SWT. JFace]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=556</guid>
		<description><![CDATA[研究SWT Layout原理的时候，找到一个视频：《Creating a Custom Window Layout in Eclipse RCP Applications》，顿时被作者使用的GridLayoutFactory和GridDataFactory惊艳了，前些天，我还傻乎乎的自己写了几个简单的类实现相同的功能，无知真可怕。本文介绍了此两个类的用法，最后有一个简单的示例。 GridLayout SWT有四种布局方式：FillLayout，RowLayout，GridLayout，FormLayout，其中使用后三种布局方式的时候，需要为每个子控件指定专门的layout data，分别是RowData，GridData和FormData，这些布局方式和相关的设置，有篇德文的文章《SWT Layout-Manager》讲解得异常清楚，不懂德文不要紧，就看里面的图就行了，在此我转载两张关于GridLayout的图： GridLayout的属性 GridData的属性 使用GridLayoutFactory 先说GridLayoutFactory，一般我们要创建一个GridLayout需要这样： GridLayout layout = new GridLayout&#40;2, false&#41;; layout.marginHeight = 10; layout.marginWidth = 10; layout.horizontalSpacing = 5; layout.verticalSpacing = 5; 而GridLayoutFactory则可以这样创建： GridLayoutFactory.fillDefaults&#40;&#41;.numColumns&#40;2&#41;.margins&#40;10, 10&#41;.spacing&#40;5, 5&#41;.create&#40;&#41;; &#8230; <a href="http://www.zhlwish.com/2011/08/05/jface_gridlayoutfactory_griddatafactory/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/DzA4-vnphOCJPUrQmhmwiws1AoM/0/da"><img src="http://feedads.g.doubleclick.net/~a/DzA4-vnphOCJPUrQmhmwiws1AoM/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/DzA4-vnphOCJPUrQmhmwiws1AoM/1/da"><img src="http://feedads.g.doubleclick.net/~a/DzA4-vnphOCJPUrQmhmwiws1AoM/1/di" border="0" ismap="true"></img></a></p><p>研究SWT Layout原理的时候，找到一个视频：<a title="Creating a Custom Window Layout in Eclipse RCP Applications" href="http://eclipse.dzone.com/tips/creating-custom-window-layout-0" target="_blank">《Creating a Custom Window Layout in Eclipse RCP Applications》</a>，顿时被作者使用的<a href="http://help.eclipse.org/indigo/index.jsp?topic=%2Forg.eclipse.platform.doc.isv%2Freference%2Fapi%2Forg%2Feclipse%2Fjface%2Flayout%2FGridLayoutFactory.html" target="_blank">GridLayoutFactory</a>和<a href="http://help.eclipse.org/indigo/index.jsp?topic=%2Forg.eclipse.platform.doc.isv%2Freference%2Fapi%2Forg%2Feclipse%2Fjface%2Flayout%2FGridDataFactory.html" target="_blank">GridDataFactory</a>惊艳了，前些天，我还傻乎乎的自己写了几个简单的类实现相同的功能，无知真可怕。本文介绍了此两个类的用法，最后有一个简单的示例。</p>
<p><span id="more-556"></span></p>
<h4>GridLayout</h4>
<p>SWT有四种布局方式：FillLayout，RowLayout，GridLayout，FormLayout，其中使用后三种布局方式的时候，需要为每个子控件指定专门的layout data，分别是RowData，GridData和FormData，这些布局方式和相关的设置，有篇德文的文章<a href="http://www.ralfebert.de/eclipse_rcp/swt_layouts1/" target="_blank">《SWT Layout-Manager》</a>讲解得异常清楚，不懂德文不要紧，就看里面的图就行了，在此我转载两张关于GridLayout的图：</p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/grid_layout_options.png" rel="lightbox[556]"><img class="size-medium wp-image-559" title="GridLayout Options" src="http://www.zhlwish.com/wp-content/uploads/2011/08/grid_layout_options-300x230.png" alt="" width="300" height="230" /></a></p>
<p style="text-align: center;">GridLayout的属性</p>
<p style="text-align: center;"><a href="http://www.zhlwish.com/wp-content/uploads/2011/08/grid_data_options.png" rel="lightbox[556]"><img class="size-medium wp-image-560 aligncenter" title="GridData Options" src="http://www.zhlwish.com/wp-content/uploads/2011/08/grid_data_options-300x300.png" alt="" width="300" height="300" /></a><br />
GridData的属性</p>
<h4>使用GridLayoutFactory</h4>
<p>先说GridLayoutFactory，一般我们要创建一个GridLayout需要这样：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #003399;">GridLayout</span> layout <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">GridLayout</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">2</span>, <span style="color: #000066; font-weight: bold;">false</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
layout.<span style="color: #006633;">marginHeight</span> <span style="color: #339933;">=</span> <span style="color: #cc66cc;">10</span><span style="color: #339933;">;</span>
layout.<span style="color: #006633;">marginWidth</span> <span style="color: #339933;">=</span> <span style="color: #cc66cc;">10</span><span style="color: #339933;">;</span>
layout.<span style="color: #006633;">horizontalSpacing</span> <span style="color: #339933;">=</span> <span style="color: #cc66cc;">5</span><span style="color: #339933;">;</span>
layout.<span style="color: #006633;">verticalSpacing</span> <span style="color: #339933;">=</span> <span style="color: #cc66cc;">5</span><span style="color: #339933;">;</span></pre></div></div>

<p>而GridLayoutFactory则可以这样创建：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">GridLayoutFactory.<span style="color: #006633;">fillDefaults</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">numColumns</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">2</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">margins</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">10</span>, <span style="color: #cc66cc;">10</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">spacing</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">5</span>, <span style="color: #cc66cc;">5</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">create</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>GridLayoutFactory的方法介绍如下：<br />
<strong>创建型</strong></p>
<table>
<tbody>
<tr>
<th> 方法</th>
<th>解释</th>
</tr>
<tr>
<td> static GridLayoutFactory createFrom(GridLayout l)</td>
<td>由已经存在的GridLayout创建新的GridLayoutFactory</td>
</tr>
<tr>
<td> static GridLayoutFactory swtDefaults()</td>
<td>
<div>创建GridLayoutFactory，他创建的GridLayout使用SWT的默认值：</div>
<div>numColumns(1)</div>
<div>margins(5,5)</div>
<div>extendedMargins(0,0,0,0)</div>
<div>spacing(5,5)</div>
<div>equalWidth(false)</div>
</td>
</tr>
<tr>
<td> static GridLayoutFactory fillDefaults()</td>
<td>
<div>创建GridLayoutFactory，他创建的GridLayout使用如下值：</div>
<div>numColumns(1)</div>
<div>margins(5,5)</div>
<div>extendedMargins(0,0,0,0)</div>
<div>spacing(5,5)</div>
<div>equalWidth(false)</div>
</td>
</tr>
<tr>
<td> GridLayoutFactory copy()</td>
<td>将已经存在的GridLayoutFactory复制一份</td>
</tr>
</tbody>
</table>
<p><strong>属性设置型</strong></p>
<table>
<tbody>
<tr>
<th> 方法</th>
<th> 解释</th>
</tr>
<tr>
<td> GridLayoutFactory equalWidth(boolean equal)</td>
<td>Grid的每一列是否宽度设为一样</td>
</tr>
<tr>
<td> GridLayoutFactory spacing(int hSpacing, int vSpacing)</td>
<td>设置单元格之间的间隔</td>
</tr>
<tr>
<td> GridLayoutFactory spacing(Point spacing)</td>
<td>设置单元格之间的间隔</td>
</tr>
<tr>
<td> GridLayoutFactory margins(Point margins)</td>
<td>设置子控件与Grid的边界的间隔</td>
</tr>
<tr>
<td> GridLayoutFactory margins(int width, int height)</td>
<td>设置子控件与Grid的边界的间隔</td>
</tr>
<tr>
<td> GridLayoutFactory extendedMargins(int left, int right, int top, int bottom)</td>
<td>设置子控件与Grid的边界的间隔</td>
</tr>
<tr>
<td> GridLayoutFactory extendedMargins(Rectangle differenceRect)</td>
<td>设置子控件与Grid的边界的间隔</td>
</tr>
<tr>
<td> GridLayoutFactory numColumns(int numColumns)</td>
<td>设置Grid的列数</td>
</tr>
</tbody>
</table>
<p><strong>其他</strong></p>
<table>
<tbody>
<tr>
<th> 方法</th>
<th> 解释</th>
</tr>
<tr>
<td> GridLayout create()</td>
<td>创建GridLayout</td>
</tr>
<tr>
<td> void applyTo(Composite c)</td>
<td>创建GridLayout并将其应用到控件上</td>
</tr>
<tr>
<td> static GridLayout copyLayout(GridLayout l)</td>
<td>复制已有的GridLayout</td>
</tr>
<tr>
<td> void generateLayout(Composite c)</td>
<td>如果控件已经其子控件没有设置GridData，则根据控件的类型生成默认GridData并且应用到控件上</td>
</tr>
</tbody>
</table>
<p>一般创建一个GridLayout然后应用到控件Composite上的方法如下：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #003399;">Composite</span> btnBar <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Composite</span><span style="color: #009900;">&#40;</span>parent, SWT.<span style="color: #006633;">NONE</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #003399;">GridLayout</span> layout <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">GridLayout</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">2</span>, <span style="color: #000066; font-weight: bold;">false</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
layout.<span style="color: #006633;">marginHeight</span> <span style="color: #339933;">=</span> <span style="color: #cc66cc;">10</span><span style="color: #339933;">;</span>
layout.<span style="color: #006633;">marginWidth</span> <span style="color: #339933;">=</span> <span style="color: #cc66cc;">10</span><span style="color: #339933;">;</span>
layout.<span style="color: #006633;">horizontalSpacing</span> <span style="color: #339933;">=</span> <span style="color: #cc66cc;">5</span><span style="color: #339933;">;</span>
layout.<span style="color: #006633;">verticalSpacing</span> <span style="color: #339933;">=</span> <span style="color: #cc66cc;">5</span><span style="color: #339933;">;</span>
btnBar.<span style="color: #006633;">setLayout</span><span style="color: #009900;">&#40;</span>layout <span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>使用GridLayoutFactory则可以简单的写成：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #003399;">Composite</span> btnBar <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Composite</span><span style="color: #009900;">&#40;</span>parent, SWT.<span style="color: #006633;">NONE</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #003399;">GridLayout</span> layout <span style="color: #339933;">=</span> GridLayoutFactory.<span style="color: #006633;">fillDefaults</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">numColumns</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">2</span><span style="color: #009900;">&#41;</span>
                                     .<span style="color: #006633;">margins</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">10</span>, <span style="color: #cc66cc;">10</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">spacing</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">5</span>, <span style="color: #cc66cc;">5</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">create</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>


<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">btnBar.<span style="color: #006633;">setLayout</span><span style="color: #009900;">&#40;</span>layout<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>或者更简单的：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #003399;">Composite</span> btnBar <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">Composite</span><span style="color: #009900;">&#40;</span>parent, SWT.<span style="color: #006633;">NONE</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
GridLayoutFactory.<span style="color: #006633;">fillDefaults</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">numColumns</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">2</span><span style="color: #009900;">&#41;</span>
                                .<span style="color: #006633;">margins</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">10</span>, <span style="color: #cc66cc;">10</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">spacing</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">5</span>, <span style="color: #cc66cc;">5</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">applyTo</span><span style="color: #009900;">&#40;</span>btnBar<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<h4>使用GridDataFactory</h4>
<p>既然同是Factory，就总有几分相似，GridDataFactory的public方法如下：</p>
<table>
<tbody>
<tr>
<th>方法</th>
<th>解释</th>
</tr>
<tr>
<td> static GridDataFactory createFrom(GridData data)</td>
<td> 从已有的GridData创建GridDataFactory</td>
</tr>
<tr>
<td> static GridDataFactory swtDefaults()</td>
<td> 创建GridDataFactory，他创建的GridData使用SWT的默认值：</p>
<div>align(SWT.BEGINNING, SWT.CENTER)</div>
<div>exclude(false)</div>
<div>grab(false, false)</div>
<div>hint(SWT.DEFAULT, SWT.DEFAULT)</div>
<div>indent(0,0)</div>
<div>minSize(0,0)</div>
<div>span(1,1)</div>
</td>
</tr>
<tr>
<td> static GridDataFactory fillDefaults()</td>
<td> 创建GridDataFactory，他创建的GridLayout使用如下值：</p>
<div>align(SWT.FILL, SWT.FILL)</div>
<div>exclude(false)</div>
<div>grab(false, false)</div>
<div>hint(SWT.DEFAULT, SWT.DEFAULT)</div>
<div>indent(0,0)</div>
<div>minSize(1,1)</div>
<div>span(1,1)</div>
</td>
</tr>
<tr>
<td> static GridDataFactory defaultsFor(Control theControl)</td>
<td>根据控件的不同类型创建GridDataFactory</td>
</tr>
<tr>
<td> static void generate(Control theControl, int hSpan, int vSpan)</td>
<td>根据控件的不同类型创建GridData，然后应用到控件上</td>
</tr>
<tr>
<td> static void generate(Control theControl, Point span)</td>
<td>根据控件的不同类型创建GridData，然后应用到控件上</td>
</tr>
<tr>
<td> GridDataFactory span(int hSpan, int vSpan)</td>
<td>设置单元格的span</td>
</tr>
<tr>
<td> GridDataFactory span(Point span)</td>
<td>设置单元格的span</td>
</tr>
<tr>
<td> GridDataFactory hint(int xHint, int yHint)</td>
<td>设置单元的宽以及高的默认值</td>
</tr>
<tr>
<td> GridDataFactory hint(Point hint)</td>
<td>设置单元的宽以及高的默认值</td>
</tr>
<tr>
<td> GridDataFactory align(int hAlign, int vAlign)</td>
<td>设置对其方式，可用值为SWT.BEGINNING, SWT.CENTER, SWT.END</td>
</tr>
<tr>
<td> GridDataFactory indent(int hIndent, int vIndent)</td>
<td>设置控件的缩进</td>
</tr>
<tr>
<td> GridDataFactory indent(Point indent)</td>
<td>设置控件的缩进</td>
</tr>
<tr>
<td> GridDataFactory grab(boolean horizontal, boolean vertical)</td>
<td>设置控件的grab属性</td>
</tr>
<tr>
<td> GridDataFactory minSize(int minX, int minY)</td>
<td>设置单元格的最小值</td>
</tr>
<tr>
<td> GridDataFactory minSize(Point min)</td>
<td>设置单元格的最小值</td>
</tr>
<tr>
<td> GridDataFactory exclude(boolean shouldExclude)</td>
<td>设置GridLayout是否将该控件放到布局中去</td>
</tr>
<tr>
<td> GridData create()</td>
<td>根据前面的设置创建GridData</td>
</tr>
<tr>
<td> GridDataFactory copy()</td>
<td>将当前的GridDataFactory复制一个新的返回</td>
</tr>
<tr>
<td> static GridData copyData(GridData data)</td>
<td>复制GridData</td>
</tr>
<tr>
<td> void applyTo(Control control)</td>
<td>使用当前的GridDataFactory创建GridData并应用到控件上</td>
</tr>
</tbody>
</table>
<p>以往在给一个控件设置GridData的代码如下：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">GridData gd <span style="color: #339933;">=</span> <span style="color: #000066; font-weight: bold;">null</span><span style="color: #339933;">;</span>
gd <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> GridData<span style="color: #009900;">&#40;</span>GridData.<span style="color: #006633;">FILL_HORIZONTAL</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
gd.<span style="color: #006633;">grabExcessHorizontalSpace</span> <span style="color: #339933;">=</span> <span style="color: #000066; font-weight: bold;">true</span><span style="color: #339933;">;</span>
txtLoginPwd.<span style="color: #006633;">setLayoutData</span><span style="color: #009900;">&#40;</span>gd<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>使用GridDataFactory则可以简单的写成：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">GridDataFactory.<span style="color: #006633;">fillDefaults</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">grab</span><span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">true</span>, <span style="color: #000066; font-weight: bold;">true</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">applyTo</span><span style="color: #009900;">&#40;</span>txtLoginPwd<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<h4>结语</h4>
<p>本文介绍了如何使用GridLayoutFactory和GridDataFactory方便编写SWT UI程序的时候使用GridLayout布局。其实，在相同的包下还有RowLayoutFactory和RowData，其使用方式和前面介绍的大同小异，只需要查看Java Doc即可以容易理解。另外，相同的包下还引入了TableColumnLayout和TreeColumnLayout两个高级的布局方式，此布局方式目前尚不清楚。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/7O1JhqEKNKs" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/05/jface_gridlayoutfactory_griddatafactory/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/05/jface_gridlayoutfactory_griddatafactory/</feedburner:origLink></item>
		<item>
		<title>Eclipse RCP中获取Plugin/Bundle中文件资源的绝对路径</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/__6eyP0xpdE/</link>
		<comments>http://www.zhlwish.com/2011/08/02/find-file-in-bundles-of-eclipse-rcp/#comments</comments>
		<pubDate>Tue, 02 Aug 2011 13:15:47 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=543</guid>
		<description><![CDATA[摘要：在进行Eclipse RCP开发的过程中，需要使用一些其他的资源（如图片、声音、配置文件、数据库等），我们一般将这些资源放到Plugin/Bundle的相应目录下（如图片资源放到icons目录，声音放到sounds目录，数据库文件放到data目录）。本文先对Eclipse Plugin和Bundle进行分析，之后讲解了如何使用Eclipse API通过这些资源的相对路径（相对于Plugin/Bundle）获取这些资源的绝对路径的方法，最后总结了org.osgi.framework.Bundle接口和FileLocator工具类的使用方法。 Bundle和Plugin Eclipse Platform架构于OSGi核心之上，每个Eclipse Plugin就是OSGi的一个Bundle，因此在Eclipse RCP中Plugin和Bundle是等价的概念。 OSGi框架中定义了org.osgi.framework.IBundle接口，表示运行于OSGi环境中的一个Bundle。Eclipse RCP中定义了org.eclipse.core.runtime.Plugin抽象类，代表一个Eclipse插件。但是Plugin抽象类并没有实现IBundle接口，而是在内部拥有一个IBundle对象实例。Plugin类实现了BundleActivator，控制其内部的IBundle对象的启动和停止，并负责将BundleContext注入到IBundle对象实例中。 我们可以发现，在IBundle接口中定义了如下几个方法，可以获取位于在Bundle文件目录中的资源： 方法 解释 URL getResource(String name); 通过Bundle的Class Loader加载资源，和Class.getResource(String)类似，注意如果当前的bundle是一个fregment，则返回null Enumeration getResources(String name) 和上面的方法一样，不过由于Eclipse插件可以包括多个Fregment，每个Fregment中可以分别包含相对路径相同的文件，因此通过一个相对路径可能找到多个匹配的资源 URL getEntry(String path); 在当前Bundle中根据Path找相应的Entry（此处的entry和resource到底有什么区别我还尚不清楚） Enumeration getEntryPaths(String path); 和上面的方法一样，同getResources(String) Enumeration findEntries(String path, String filePattern, boolean recurse); 根据path和pattern找相应的资源文件，可以使用通配符，如需要查找所有语言文件： bundle.findEntries(“OSGI-INF/l10n”, &#8230; <a href="http://www.zhlwish.com/2011/08/02/find-file-in-bundles-of-eclipse-rcp/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/bZ6-_3XGkUeMRv5qnb2pcqFD8dc/0/da"><img src="http://feedads.g.doubleclick.net/~a/bZ6-_3XGkUeMRv5qnb2pcqFD8dc/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/bZ6-_3XGkUeMRv5qnb2pcqFD8dc/1/da"><img src="http://feedads.g.doubleclick.net/~a/bZ6-_3XGkUeMRv5qnb2pcqFD8dc/1/di" border="0" ismap="true"></img></a></p><p>摘要：在进行Eclipse RCP开发的过程中，需要使用一些其他的资源（如图片、声音、配置文件、数据库等），我们一般将这些资源放到Plugin/Bundle的相应目录下（如图片资源放到icons目录，声音放到sounds目录，数据库文件放到data目录）。本文先对Eclipse Plugin和Bundle进行分析，之后讲解了如何使用Eclipse API通过这些资源的相对路径（相对于Plugin/Bundle）获取这些资源的绝对路径的方法，最后总结了org.osgi.framework.Bundle接口和FileLocator工具类的使用方法。<br />
<span id="more-543"></span></p>
<p><strong>Bundle和Plugin</strong></p>
<p>Eclipse Platform架构于OSGi核心之上，每个Eclipse Plugin就是OSGi的一个Bundle，因此在Eclipse RCP中Plugin和Bundle是等价的概念。</p>
<p>OSGi框架中定义了org.osgi.framework.IBundle接口，表示运行于OSGi环境中的一个Bundle。Eclipse RCP中定义了org.eclipse.core.runtime.Plugin抽象类，代表一个Eclipse插件。但是Plugin抽象类并没有实现IBundle接口，而是在内部拥有一个IBundle对象实例。Plugin类实现了BundleActivator，控制其内部的IBundle对象的启动和停止，并负责将BundleContext注入到IBundle对象实例中。</p>
<p>我们可以发现，在IBundle接口中定义了如下几个方法，可以获取位于在Bundle文件目录中的资源：</p>
<table>
<tbody>
<tr>
<th width="40%">方法</th>
<th>解释</th>
</tr>
<tr>
<td>URL getResource(String name);</td>
<td>通过Bundle的Class Loader加载资源，和Class.getResource(String)类似，注意如果当前的bundle是一个fregment，则返回null</td>
</tr>
<tr>
<td>Enumeration getResources(String name)</td>
<td>和上面的方法一样，不过由于Eclipse插件可以包括多个Fregment，每个Fregment中可以分别包含相对路径相同的文件，因此通过一个相对路径可能找到多个匹配的资源</td>
</tr>
<tr>
<td>URL getEntry(String path);</td>
<td>在当前Bundle中根据Path找相应的Entry（此处的entry和resource到底有什么区别我还尚不清楚）</td>
</tr>
<tr>
<td>Enumeration getEntryPaths(String path);</td>
<td>和上面的方法一样，同getResources(String)</td>
</tr>
<tr>
<td>Enumeration findEntries(String path, String filePattern,<br />
boolean recurse);</td>
<td>根据path和pattern找相应的资源文件，可以使用通配符，如需要查找所有语言文件：<br />
bundle.findEntries(“OSGI-INF/l10n”, “*.properties”, true);</td>
</tr>
</tbody>
</table>
<p><strong>如何获取当前的Bundle对象</strong></p>
<p>开发Eclipse Plugin/Bundle应用首先需要创建Activator类，继承自org.eclipse.ui.plugin.AbstractUIPlugin，该类继承自上文提到的org.eclipse.core.runtime.Plugin类，OSGi框架在加载Plugin/Bundle的时候首先加载此Activator类，然后调用此类中定义的start(BundleContext context)和stop(BundleContext context)方法启动和停止这个Plugin/Bundle。在这个类的父类Plugin中声明了Bundle类型实例，可以通过getBundle()方法获取这个Bundle实例。</p>
<p>以下代码为Activator类中的start(BundleContext)方法，在其中调用了getResource(String)和getEntry(String)两个方法，同时调用FileLocator.toFileURL(String)将URL转化为文件系统的路径</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> start<span style="color: #009900;">&#40;</span>BundleContext context<span style="color: #009900;">&#41;</span> <span style="color: #000000; font-weight: bold;">throws</span> <span style="color: #003399;">Exception</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #000000; font-weight: bold;">super</span>.<span style="color: #006633;">start</span><span style="color: #009900;">&#40;</span>context<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	plugin <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">this</span><span style="color: #339933;">;</span>
	<span style="color: #003399;">System</span>.<span style="color: #006633;">out</span>.<span style="color: #006633;">println</span><span style="color: #009900;">&#40;</span><span style="color: #003399;">Activator</span>.<span style="color: #006633;">getDefault</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getBundle</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getLocation</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #003399;">URL</span> url <span style="color: #339933;">=</span> <span style="color: #003399;">Activator</span>.<span style="color: #006633;">getDefault</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getBundle</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getResource</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;META-INF/MANIFEST.MF&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #003399;">System</span>.<span style="color: #006633;">out</span>.<span style="color: #006633;">println</span><span style="color: #009900;">&#40;</span>url<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #003399;">System</span>.<span style="color: #006633;">out</span>.<span style="color: #006633;">println</span><span style="color: #009900;">&#40;</span>FileLocator.<span style="color: #006633;">toFileURL</span><span style="color: #009900;">&#40;</span>url<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #003399;">URL</span> url2 <span style="color: #339933;">=</span> <span style="color: #003399;">Activator</span>.<span style="color: #006633;">getDefault</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getBundle</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getEntry</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;META-INF/MANIFEST.MF&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #003399;">System</span>.<span style="color: #006633;">out</span>.<span style="color: #006633;">println</span><span style="color: #009900;">&#40;</span>url2<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #003399;">System</span>.<span style="color: #006633;">out</span>.<span style="color: #006633;">println</span><span style="color: #009900;">&#40;</span>FileLocator.<span style="color: #006633;">toFileURL</span><span style="color: #009900;">&#40;</span>url2<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>上面代码输出结果为：</p>
<pre><strong>reference:file</strong>:/D:/demo/modeling-workspace/com.zhlwish.proppagedemo/
<strong>bundleresource</strong>://709.fwk15218962:1/META-INF/MANIFEST.MF
<strong>file</strong>:/D:/demo/modeling-workspace/com.zhlwish.proppagedemo/META-INF/MANIFEST.MF
<strong>bundleentry</strong>://709.fwk15218962/META-INF/MANIFEST.MF
<strong>file</strong>:/D:/demo/modeling-workspace/com.zhlwish.proppagedemo/META-INF/MANIFEST.MF</pre>
<p>通过结果可以很明显看到，使用getResource(String)和getEntry(String)获取到的URL是OSGi环境中的路径，需要通过FileLocator.toFileURL(String)方法将OSGi环境中的URL转化为文件系统中的URL。</p>
<p>至于getResource()和getEntry()有什么区别，我到Eclipse Forum里面提了问题，回答是：</p>
<ol>
<li>getResource uses the bundle&#8217;s class loader to load a resource. This resource could come from imported constraints (Import-Package, Require-Bundle) or from the local bundle classpath.</li>
<li>getEntry only searches the bundles jar files itself and does not consider any constraints or the bundle&#8217;s class path (Bundle-ClassPath header).”</li>
</ol>
<p>详见<a href="http://www.eclipse.org/forums/index.php/m/710032/#msg_710032" target="_blank">http://www.eclipse.org/forums/index.php/m/710032/#msg_710032</a></p>
<p><strong>FileLocator</strong></p>
<p>在上文已经提到FileLocator的toFileUrl(String)方法，FileLocator是一个工具类，其目的就是在Bundle中查找相应的资源文件，其本身定义了如下几个方法：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">URL</span> find<span style="color: #009900;">&#40;</span>Bundle bundle, IPath path, <span style="color: #003399;">Map</span> override<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">URL</span> find<span style="color: #009900;">&#40;</span><span style="color: #003399;">URL</span> url<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">URL</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> findEntries<span style="color: #009900;">&#40;</span>Bundle bundle, IPath path<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">URL</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> findEntries<span style="color: #009900;">&#40;</span>Bundle bundle, IPath path, <span style="color: #003399;">Map</span> override<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">File</span> getBundleFile<span style="color: #009900;">&#40;</span>Bundle bundle<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">InputStream</span> openStream<span style="color: #009900;">&#40;</span>Bundle bundle, IPath file, <span style="color: #000066; font-weight: bold;">boolean</span> substituteArgs<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">URL</span> resolve<span style="color: #009900;">&#40;</span><span style="color: #003399;">URL</span> url<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">static</span> <span style="color: #003399;">URL</span> toFileURL<span style="color: #009900;">&#40;</span><span style="color: #003399;">URL</span> url<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>看起来和Bundle中的方法那么的相似，归根结底，FileLocator中的方法也都是通过调用Bundle中的相对应方法来实现其功能的，除了resolve(URL)和toFileURL(URL)，后者之前演示过其功能，前者的功能也同样是将OSGi环境中的URL解析成为文件系统中的URL。其实我不认为此FileLocator除去toFileURL()此方法外地其他方法有更好的地方，如果可能，还是直接用Bundle的方法更好。</p>
<p><strong>总结</strong></p>
<p>很明显，在Bundle中查找文件资源需要通过FileLocator和Bundle两个类的协作才能完成，由于一般情况下Eclipse RCP的属性以及配置值存放于Eclipse Workspace中，从Bundle中读取资源的需求比较少。最主要的应用场景是，一些图片资源可以通过此方式读取，然后在Eclipse RCP应用中处理和显示。</p>
<pre><span class="Apple-style-span" style="font-family: Georgia, 'Times New Roman', 'Bitstream Charter', Times, serif; font-size: 13px; line-height: 19px; white-space: normal;">关于Eclipse RCP开发的其他文章：</span></pre>
<ol>
<li><a title="Eclipse RCP 中 Part 和 Site、菜单和工具栏" href="http://www.zhlwish.com/2011/07/25/eclipse-rcp-part-and-site/" target="_blank">Eclipse RCP 中 Part 和 Site、菜单和工具栏</a></li>
<li><a title="Eclipse RCP开发中关于Image(图片)的API使用" href="http://www.zhlwish.com/2011/07/18/eclipse-rcp-image-api/" target="_blank">Eclipse RCP开发中关于Image(图片)的API使用</a></li>
<li><a title="Eclipse RCP中的日志" href="http://www.zhlwish.com/2011/07/13/eclipse-rcp-plugin-log/" target="_blank">Eclipse RCP中的日志</a></li>
</ol>
<p>本文是本博客原创文章，您可以自由转载，但转载请注明来源。</p>
<p>&lt;全文完&gt;</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/__6eyP0xpdE" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/08/02/find-file-in-bundles-of-eclipse-rcp/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/08/02/find-file-in-bundles-of-eclipse-rcp/</feedburner:origLink></item>
		<item>
		<title>Eclipse RCP 中 Part 和 Site、菜单和工具栏</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/2EYwx69-5fY/</link>
		<comments>http://www.zhlwish.com/2011/07/25/eclipse-rcp-part-and-site/#comments</comments>
		<pubDate>Mon, 25 Jul 2011 13:16:16 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=535</guid>
		<description><![CDATA[在进行 Eclipse RCP 开发的时候，由于 GUI 系统和 Eclipse 平台本身的复杂性，让我们很难理顺各种组件之间的关系，本文对 Eclipse RCP 的 GUI 组成结构进行分析，解释了 Workbench，Workbench Window，Workbench Page，Workbench Part，View Part 和 Editor Part 以及其相互之间的关系。并对和上述组件关系紧密的形如 I**Site 的类（包括 IWorkbenchSite，IWorkbenchPartSite，IPageSite，IViewSite，IEditorSite）进行了分析。 本文最后给出了一个在自定义 View 中加入上下文菜单、工具栏和下拉菜单的示例。 本文的全文PDF文件请点击《Eclipse RCP 中 Part 和 Site、菜单和工具栏》下载 本人撰写的其他Eclipse RCP文章： Eclipse RCP中的日志 Eclipse RCP开发中关于Image(图片)的API使用 &#8230; <a href="http://www.zhlwish.com/2011/07/25/eclipse-rcp-part-and-site/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/-J5mV5DbKVUtd4QfzFHFw_pspn4/0/da"><img src="http://feedads.g.doubleclick.net/~a/-J5mV5DbKVUtd4QfzFHFw_pspn4/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/-J5mV5DbKVUtd4QfzFHFw_pspn4/1/da"><img src="http://feedads.g.doubleclick.net/~a/-J5mV5DbKVUtd4QfzFHFw_pspn4/1/di" border="0" ismap="true"></img></a></p><p>在进行 Eclipse RCP 开发的时候，由于 GUI 系统和 Eclipse 平台本身的复杂性，让我们很难理顺各种组件之间的关系，本文对 Eclipse RCP 的 GUI 组成结构进行分析，解释了 Workbench，Workbench Window，Workbench Page，Workbench Part，View Part 和 Editor Part 以及其相互之间的关系。并对和上述组件关系紧密的形如 I**Site 的类（包括 IWorkbenchSite，IWorkbenchPartSite，IPageSite，IViewSite，IEditorSite）进行了分析。<br />
本文最后给出了一个在自定义 View 中加入上下文菜单、工具栏和下拉菜单的示例。<br />
<span id="more-535"></span><br />
本文的全文PDF文件请点击<a href='http://www.zhlwish.com/wp-content/uploads/2011/07/eclipse-part-site.pdf'>《Eclipse RCP 中 Part 和 Site、菜单和工具栏》</a>下载</p>
<p>本人撰写的其他Eclipse RCP文章：</p>
<ol>
<li><a href="http://www.zhlwish.com/2011/07/13/eclipse-rcp-plugin-log/" title="Eclipse RCP中的日志" target="_blank">Eclipse RCP中的日志</a></li>
<li>
<a href="http://www.zhlwish.com/2011/07/18/eclipse-rcp-image-api/" title="Eclipse RCP开发中关于Image(图片)的API使用" target="_blank">Eclipse RCP开发中关于Image(图片)的API使用</a></li>
</ol>
<p>本文是本博客原创文章，您可以自由转载，但转载请注明来源。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/2EYwx69-5fY" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/07/25/eclipse-rcp-part-and-site/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/07/25/eclipse-rcp-part-and-site/</feedburner:origLink></item>
		<item>
		<title>用Bash一行一行的读取文件</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/68OAJXvCOpw/</link>
		<comments>http://www.zhlwish.com/2011/07/22/read_file_line_by_line_with_bash/#comments</comments>
		<pubDate>Fri, 22 Jul 2011 06:47:59 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>
		<category><![CDATA[bash]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[shell]]></category>
		<category><![CDATA[ubuntu]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=445</guid>
		<description><![CDATA[将配置信息写在文本文件中，使用bash一行一行的读取文本文件，然后执行相应的操作，是非常常见的需求，本文使用了shell脚本的while循环和read命令非常简单的达到了目的 其实我的目标是用git下载Eclipse的源代码，Eclipse的源代码是用CVS管理的，会自动同步到Eclipse的git仓库，仓库地址为：http://dev.eclipse.org/git/index.html。 我复制了git仓库的url到一个文本文件urls中，一行一个： http://dev.eclipse.org/git/org.eclipse.pde/apitools.git http://dev.eclipse.org/git/org.eclipse.pde/build.git http://dev.eclipse.org/git/org.eclipse.pde/doc.git http://dev.eclipse.org/git/org.eclipse.pde/ds.git http://dev.eclipse.org/git/org.eclipse.pde/org.eclipse.pde.releng.git http://dev.eclipse.org/git/org.eclipse.pde/ua.git http://dev.eclipse.org/git/org.eclipse.pde/ui.git http://dev.eclipse.org/git/org.eclipse.pde/visualization.git 然后想办法读取这个文本文件，执行git clone命令： cat urls &#124; while read line; do git clone ${line}; done 上面的命令其实是四条命令， cat urls是第一条，将文本文件中的内容输出到标注输出，urls是文本文件名称； while read line是第二条，循环读取标准输入，存放到line变量中，read命令请见参考1； do git clone ${line}是第三条，克隆git仓库到本地文件夹中，git默认为将“xxx.git”中的“.git”去掉，取“xxx”作为克隆项目的目录名称，关于git请见参考3； done是第四条，标示while语句的结束 如果两条命令写在同一行则需要用;号隔开，一行只写一条命令就不需要写;号了。while后面的子命令通常是测试命令，在本例中，读取文件结束，read返回0，循环结束。关于shell请见参考2。 ls -d */ &#124; &#8230; <a href="http://www.zhlwish.com/2011/07/22/read_file_line_by_line_with_bash/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/CQUT-Ytri0TGq-AHLOmHTVW9Tt4/0/da"><img src="http://feedads.g.doubleclick.net/~a/CQUT-Ytri0TGq-AHLOmHTVW9Tt4/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/CQUT-Ytri0TGq-AHLOmHTVW9Tt4/1/da"><img src="http://feedads.g.doubleclick.net/~a/CQUT-Ytri0TGq-AHLOmHTVW9Tt4/1/di" border="0" ismap="true"></img></a></p><p>将配置信息写在文本文件中，使用bash一行一行的读取文本文件，然后执行相应的操作，是非常常见的需求，本文使用了shell脚本的while循环和read命令非常简单的达到了目的</p>
<p><span id="more-445"></span>其实我的目标是用git下载Eclipse的源代码，Eclipse的源代码是用CVS管理的，会自动同步到Eclipse的git仓库，仓库地址为：<a title="Eclipse Git Repository" href="http://dev.eclipse.org/git/index.html" target="_blank">http://dev.eclipse.org/git/index.html</a>。</p>
<p>我复制了git仓库的url到一个文本文件urls中，一行一个：</p>
<pre>http://dev.eclipse.org/git/org.eclipse.pde/apitools.git

http://dev.eclipse.org/git/org.eclipse.pde/build.git

http://dev.eclipse.org/git/org.eclipse.pde/doc.git

http://dev.eclipse.org/git/org.eclipse.pde/ds.git

http://dev.eclipse.org/git/org.eclipse.pde/org.eclipse.pde.releng.git

http://dev.eclipse.org/git/org.eclipse.pde/ua.git

http://dev.eclipse.org/git/org.eclipse.pde/ui.git

http://dev.eclipse.org/git/org.eclipse.pde/visualization.git</pre>
<p>然后想办法读取这个文本文件，执行git clone命令：</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:Verdana,Courier New;"><span style="color: #c20cb9; font-weight: bold;">cat</span> urls <span style="color: #000000; font-weight: bold;">|</span> <span style="color: #000000; font-weight: bold;">while</span> <span style="color: #c20cb9; font-weight: bold;">read</span> line; <span style="color: #000000; font-weight: bold;">do</span> <span style="color: #c20cb9; font-weight: bold;">git</span> clone <span style="color: #800000;">${line}</span>; <span style="color: #000000; font-weight: bold;">done</span></pre></div></div>

<p>上面的命令其实是四条命令，</p>
<ol>
<li>cat urls是第一条，将文本文件中的内容输出到标注输出，urls是文本文件名称；</li>
<li>while read line是第二条，循环读取标准输入，存放到line变量中，read命令请见<a href="#ref" target="_self">参考1</a>；</li>
<li>do git clone ${line}是第三条，克隆git仓库到本地文件夹中，git默认为将“xxx.git”中的“.git”去掉，取“xxx”作为克隆项目的目录名称，关于git请见<a href="#ref" target="_self">参考3</a>；</li>
<li>done是第四条，标示while语句的结束</li>
</ol>
<p>如果两条命令写在同一行则需要用;号隔开，一行只写一条命令就不需要写;号了。while后面的子命令通常是测试命令，在本例中，读取文件结束，read返回0，循环结束。关于shell请见<a href="#ref" target="_self">参考2</a>。</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:Verdana,Courier New;"><span style="color: #c20cb9; font-weight: bold;">ls</span> <span style="color: #660033;">-d</span> <span style="color: #000000; font-weight: bold;">*/</span> <span style="color: #000000; font-weight: bold;">|</span> <span style="color: #000000; font-weight: bold;">while</span> <span style="color: #c20cb9; font-weight: bold;">read</span> line; <span style="color: #000000; font-weight: bold;">do</span> <span style="color: #7a0874; font-weight: bold;">cd</span> <span style="color: #800000;">${line}</span>; <span style="color: #c20cb9; font-weight: bold;">git</span> pull origin master; <span style="color: #7a0874; font-weight: bold;">cd</span> ..; <span style="color: #000000; font-weight: bold;">done</span></pre></div></div>

<p>在克隆了git仓库后，还需要执行“git pull”命令更新仓库，仿照上例即可写出上面的代码。</p>
<p>“ls -d */”输出当前文件夹下的文件夹名称，虽然在控制台里面看起来输出在一行，但是实际上用下面的命令就会发现其实每个文件夹名称都是在单独的一行的，关于wc请见<a href="#ref" target="_self">参考4</a>。</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:Verdana,Courier New;"><span style="color: #c20cb9; font-weight: bold;">ls</span> <span style="color: #660033;">-d</span> <span style="color: #000000; font-weight: bold;">*/</span> <span style="color: #000000; font-weight: bold;">|</span> <span style="color: #c20cb9; font-weight: bold;">wc</span> <span style="color: #660033;">-l</span></pre></div></div>

<p><a name="ref"></a>参考：</p>
<ol>
<li><a title="read MAN Page" href="http://ss64.com/bash/read.html" target="_blank">read MAN Page</a></li>
<li><a title="Shell脚本语法" href="http://learn.akae.cn/media/ch31s05.html" target="_blank">Shell脚本语法</a></li>
<li><a title="" href="http://www-cs-students.stanford.edu/~blynn/gitmagic/intl/zh_cn/index.html" target="_blank">Git Magic 中文版</a></li>
<li><a href="http://linux.die.net/man/1/wc" target="_blank">wc MAN Page</a></li>
</ol>
<div>本文是本博客原创文章，您可以自由转载，但转载请注明来源。</div>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/68OAJXvCOpw" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/07/22/read_file_line_by_line_with_bash/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/07/22/read_file_line_by_line_with_bash/</feedburner:origLink></item>
		<item>
		<title>Java播放音乐资料收集</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/V42ju_kuCqU/</link>
		<comments>http://www.zhlwish.com/2011/07/21/java-play-music/#comments</comments>
		<pubDate>Wed, 20 Jul 2011 17:20:44 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Java]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=441</guid>
		<description><![CDATA[Java播放音乐比较麻烦，主要原因是Java的跨平台导致。Java的播放音乐的API主要包括两部分，一是Java SE里面包含的Java Sound API，二是作为独立于Java SE之外的Java Music Framework。两者的主要差别在于所支持的声音文件格式不同。 本文只是对相关技术进行了简单罗列，收集了相关的链接地址，需要深入了解请进入相关链接深入阅读。 Java平台提供的sound API 支持的音频文件格式只有AIFF，AU，WAV 支持的音乐文件格式有MIDI，RMF(Rich Music Format) 声音格式：8位和16位单声道以及立体声音频数据，采样率在8khz和48khz之间 Java sound api简介 JavaTM Sound Programmer Guide Java Sound API: Java Sound Demo 使用第三方的库播放MP3格式的音乐 How to Play an MP3 File in Java：JLayer MP3 Library 使用Java &#8230; <a href="http://www.zhlwish.com/2011/07/21/java-play-music/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/B8XmwiVFgpfHHUWLJWLtwHIJmQA/0/da"><img src="http://feedads.g.doubleclick.net/~a/B8XmwiVFgpfHHUWLJWLtwHIJmQA/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/B8XmwiVFgpfHHUWLJWLtwHIJmQA/1/da"><img src="http://feedads.g.doubleclick.net/~a/B8XmwiVFgpfHHUWLJWLtwHIJmQA/1/di" border="0" ismap="true"></img></a></p><p>Java播放音乐比较麻烦，主要原因是Java的跨平台导致。Java的播放音乐的API主要包括两部分，一是Java SE里面包含的Java Sound API，二是作为独立于Java SE之外的Java Music Framework。两者的主要差别在于所支持的声音文件格式不同。</p>
<p>本文只是对相关技术进行了简单罗列，收集了相关的链接地址，需要深入了解请进入相关链接深入阅读。<br />
<span id="more-441"></span></p>
<p><strong>Java平台提供的sound API</strong><br />
支持的音频文件格式只有AIFF，AU，WAV<br />
支持的音乐文件格式有MIDI，RMF(Rich Music Format)<br />
声音格式：8位和16位单声道以及立体声音频数据，采样率在8khz和48khz之间</p>
<ul>
<li><a href="http://download.oracle.com/javase/1.5.0/docs/guide/sound/" target="_blank">Java sound api简介</a></li>
<li><a href="http://download.oracle.com/javase/1.5.0/docs/guide/sound/programmer_guide/contents.html" target="_blank">JavaTM Sound Programmer Guide</a></li>
<li><a href="http://java.sun.com/products/java-media/sound/samples/JavaSoundDemo/" target="_blank">Java Sound API: Java Sound Demo</a></li>
</ul>
<p><strong>使用第三方的库播放MP3格式的音乐</strong><br />
<a href="http://introcs.cs.princeton.edu/java/faq/mp3/mp3.html" target="_blank">How to Play an MP3 File in Java：JLayer MP3 Library</a></p>
<p><strong>使用Java Music Framework播放MP3格式的音乐</strong></p>
<ol>
<li><a href="http://www.ntu.edu.sg/home/ehchua/programming/java/J8c_PlayingSound.html" target="_blank">Java Game Programming: Playing Sound</a>：该文中介绍了如何使用Java Media Framework播放MP3格式的音乐</li>
<li><a href="http://www.oracle.com/technetwork/java/javase/tech/index-jsp-140239.html " target="_blank">JMF主页</a></li>
<li><a href="http://www.oracle.com/technetwork/java/javase/specdownload-136569.html" target="_blank">JMF现在的最新版本为2.0，API下载地址</a></li>
</ol>
<p>JMF播放MP3示例代码：请把音乐放到Eclipse工程目录的跟目录下（和src目录同级别）</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">package</span> <span style="color: #006699;">com.zhlwish.javasound</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.io.File</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.io.IOException</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.net.URL</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">javax.media.*</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> Main <span style="color: #009900;">&#123;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">private</span> Player player<span style="color: #339933;">;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000066; font-weight: bold;">void</span> main<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> args<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
        Main m <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Main<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        m.<span style="color: #006633;">play</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;可惜不是你.mp3&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> play<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> fileName<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000000; font-weight: bold;">try</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #003399;">File</span> file <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">File</span><span style="color: #009900;">&#40;</span>fileName<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            <span style="color: #003399;">URL</span> url <span style="color: #339933;">=</span> file.<span style="color: #006633;">toURI</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">toURL</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            MediaLocator locator <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> MediaLocator<span style="color: #009900;">&#40;</span>url<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            player <span style="color: #339933;">=</span> Manager.<span style="color: #006633;">createPlayer</span><span style="color: #009900;">&#40;</span>locator<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            player.<span style="color: #006633;">addControllerListener</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> ControllerListener<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
                <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> controllerUpdate<span style="color: #009900;">&#40;</span>ControllerEvent event<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
                    <span style="color: #000000; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>event <span style="color: #000000; font-weight: bold;">instanceof</span> EndOfMediaEvent<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
                        player.<span style="color: #006633;">stop</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
                        player.<span style="color: #006633;">close</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
                    <span style="color: #009900;">&#125;</span>
                <span style="color: #009900;">&#125;</span>
            <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            player.<span style="color: #006633;">realize</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            player.<span style="color: #006633;">start</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span> <span style="color: #000000; font-weight: bold;">catch</span> <span style="color: #009900;">&#40;</span>NoPlayerException e<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            e.<span style="color: #006633;">printStackTrace</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span> <span style="color: #000000; font-weight: bold;">catch</span> <span style="color: #009900;">&#40;</span><span style="color: #003399;">IOException</span> e<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            e.<span style="color: #006633;">printStackTrace</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Java播放MIDI实例代码：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;">AudioPlayer mgp <span style="color: #339933;">=</span> AudioPlayer.<span style="color: #006633;">player</span><span style="color: #339933;">;</span>
AudioStream bgm<span style="color: #339933;">;</span>
AudioData md<span style="color: #339933;">;</span>
ContinuousAudioDataStream loop <span style="color: #339933;">=</span> <span style="color: #000066; font-weight: bold;">null</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">try</span><span style="color: #009900;">&#123;</span>
    bgm <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> AudioStream<span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">FileInputStream</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    md <span style="color: #339933;">=</span> bgm.<span style="color: #006633;">getData</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    loop <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> ContinuousAudioDataStream <span style="color: #009900;">&#40;</span>md<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span><span style="color: #000000; font-weight: bold;">catch</span><span style="color: #009900;">&#40;</span><span style="color: #003399;">Exception</span> e<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    e.<span style="color: #006633;">printStackTrace</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
mgp.<span style="color: #006633;">start</span><span style="color: #009900;">&#40;</span>loop<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p><strong>2011-7-28更新：</strong></p>
<p>JMF在某些联想(Lenovo)的机器上安装失败，不清楚具体原因，而且JMF已经年久失修，不推荐使用。<br />
最新推荐的是本文中曾提到，但是一笔带过的一个库（内疚中&#8230;）,叫JLayer，里面自带两个后台播放器实现Player和AdvancedPlayer，具体的使用方法可以参考<a href="http://www.youtube.com/watch?v=f-7cgX_I220" title="Java Program Play A MP3 File Using JLayer">http://www.youtube.com/watch?v=f-7cgX_I220</a></p>
<p>我摘抄了部分代码如下：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #003399;">File</span> file <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">File</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;xxx.mp3&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #003399;">FileInputStream</span> fInputStream <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">FileInputStream</span><span style="color: #009900;">&#40;</span>file<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
Player p <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Player<span style="color: #009900;">&#40;</span>fInputStream<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
p.<span style="color: #006633;">play</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/V42ju_kuCqU" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/07/21/java-play-music/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/07/21/java-play-music/</feedburner:origLink></item>
		<item>
		<title>Eclipse RCP开发中关于Image(图片)的API使用</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/vXfAZt-P3I0/</link>
		<comments>http://www.zhlwish.com/2011/07/18/eclipse-rcp-image-api/#comments</comments>
		<pubDate>Mon, 18 Jul 2011 14:06:28 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[Eclispe RCP]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=434</guid>
		<description><![CDATA[Eclipse RCP开发中的Image API分为两个层次，一个是SWT层，另一个是JFace层面的。 SWT层面的API中的类主要包括Image，ImageData和ImageLoader三个，JFace层面的API中的类主要包括ImageDescriptor和ImageRegistry。 本文的全文PDF文件请点击《Eclipse RCP开发中关于Image(图片)的API使用》下载]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/JLIV4XW9HpWjwS4CXHcdsEO4Z_s/0/da"><img src="http://feedads.g.doubleclick.net/~a/JLIV4XW9HpWjwS4CXHcdsEO4Z_s/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/JLIV4XW9HpWjwS4CXHcdsEO4Z_s/1/da"><img src="http://feedads.g.doubleclick.net/~a/JLIV4XW9HpWjwS4CXHcdsEO4Z_s/1/di" border="0" ismap="true"></img></a></p><p>Eclipse RCP开发中的Image API分为两个层次，一个是SWT层，另一个是JFace层面的。</p>
<p>SWT层面的API中的类主要包括Image，ImageData和ImageLoader三个，JFace层面的API中的类主要包括ImageDescriptor和ImageRegistry。</p>
<p><span id="more-434"></span></p>
<p>本文的全文PDF文件请点击<a href="http://www.zhlwish.com/wp-content/uploads/2011/07/Eclipse-RCP开发中关于Image图片的API使用.pdf">《Eclipse RCP开发中关于Image(图片)的API使用》</a>下载</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/vXfAZt-P3I0" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/07/18/eclipse-rcp-image-api/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/07/18/eclipse-rcp-image-api/</feedburner:origLink></item>
		<item>
		<title>Eclipse RCP中的日志</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/v1_Wap_e1Ho/</link>
		<comments>http://www.zhlwish.com/2011/07/13/eclipse-rcp-plugin-log/#comments</comments>
		<pubDate>Wed, 13 Jul 2011 05:02:11 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Eclipse RCP]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[log]]></category>
		<category><![CDATA[rcp]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=422</guid>
		<description><![CDATA[完成Eclipse RCP平台日志功能是核心接口为：org.eclipse.core.runtime.ILog org.eclipse.core.internal.runtime.Log实现了该接口，主要方法如下： 构造函数： public Log&#40;Bundle plugin&#41; 方法： public void log&#40;final IStatus status&#41; 一般情况下插件的Activator继承自AbstractPlugin，也间接继承自Plugin，org.eclipse.core.runtime.Plugin中定义了: public final ILog getLog&#40;&#41; 通过该方法直接返回ILog实例，如果当前插件中没有ILog实例，则创建一个新的实例返回 另一个相关的接口是org.eclipse.core.runtime.IStatus，org.eclipse.core.runtime.Status类实现了这个接口，其构造函数如下： public Status&#40;int severity, String pluginId, int code, String message, Throwable exception&#41; 其中： severity为消息级别，在IStatus中有定义 pluginId为插件实例的ID code为消息类型编码，一般为IStatus.OK，各个Plugin可以自行定义status code message为消息内容 exception为异常实例，可以为null 示例： import &#8230; <a href="http://www.zhlwish.com/2011/07/13/eclipse-rcp-plugin-log/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/CcHOlH43vKsywNM20aKtDfJPBio/0/da"><img src="http://feedads.g.doubleclick.net/~a/CcHOlH43vKsywNM20aKtDfJPBio/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/CcHOlH43vKsywNM20aKtDfJPBio/1/da"><img src="http://feedads.g.doubleclick.net/~a/CcHOlH43vKsywNM20aKtDfJPBio/1/di" border="0" ismap="true"></img></a></p><p>完成Eclipse RCP平台日志功能是核心接口为：org.eclipse.core.runtime.ILog</p>
<p>org.eclipse.core.internal.runtime.Log实现了该接口，主要方法如下：</p>
<p>构造函数：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> Log<span style="color: #009900;">&#40;</span>Bundle plugin<span style="color: #009900;">&#41;</span></pre></div></div>

<p>方法：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000066; font-weight: bold;">void</span> log<span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">final</span> IStatus status<span style="color: #009900;">&#41;</span></pre></div></div>

<p><span id="more-422"></span><br />
一般情况下插件的Activator继承自AbstractPlugin，也间接继承自Plugin，org.eclipse.core.runtime.Plugin中定义了:</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">final</span> ILog getLog<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>通过该方法直接返回ILog实例，如果当前插件中没有ILog实例，则创建一个新的实例返回</p>
<p>另一个相关的接口是org.eclipse.core.runtime.IStatus，org.eclipse.core.runtime.Status类实现了这个接口，其构造函数如下：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">public</span> Status<span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">int</span> severity, <span style="color: #003399;">String</span> pluginId, <span style="color: #000066; font-weight: bold;">int</span> code, 
               <span style="color: #003399;">String</span> message, <span style="color: #003399;">Throwable</span> exception<span style="color: #009900;">&#41;</span></pre></div></div>

<p>其中：
<ol>
<li>severity为消息级别，在IStatus中有定义</li>
<li>pluginId为插件实例的ID</li>
<li>code为消息类型编码，一般为IStatus.OK，各个Plugin可以自行定义status code</li>
<li>message为消息内容</li>
<li>exception为异常实例，可以为null</li>
</ol>
<p>示例：</p>

<div class="wp_syntax"><div class="code"><pre class="java" style="font-family:Verdana,Courier New;"><span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.core.runtime.ILog</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.core.runtime.IStatus</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">org.eclipse.core.runtime.Status</span><span style="color: #339933;">;</span>
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> LogUtils <span style="color: #009900;">&#123;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000066; font-weight: bold;">void</span> logInfo<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> message<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        log<span style="color: #009900;">&#40;</span>IStatus.<span style="color: #006633;">INFO</span>, IStatus.<span style="color: #006633;">OK</span>, message, <span style="color: #000066; font-weight: bold;">null</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000066; font-weight: bold;">void</span> logError<span style="color: #009900;">&#40;</span><span style="color: #003399;">Throwable</span> exception<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        logError<span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;Unexpected Exception&quot;</span>, exception<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000066; font-weight: bold;">void</span> logError<span style="color: #009900;">&#40;</span><span style="color: #003399;">String</span> message, <span style="color: #003399;">Throwable</span> exception<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        log<span style="color: #009900;">&#40;</span>IStatus.<span style="color: #006633;">ERROR</span>, IStatus.<span style="color: #006633;">OK</span>, message, exception<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000066; font-weight: bold;">void</span> log<span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">int</span> severity, <span style="color: #000066; font-weight: bold;">int</span> code, <span style="color: #003399;">String</span> message,
            <span style="color: #003399;">Throwable</span> exception<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        log<span style="color: #009900;">&#40;</span>createStatus<span style="color: #009900;">&#40;</span>severity, code, message, exception<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> IStatus createStatus<span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">int</span> severity, <span style="color: #000066; font-weight: bold;">int</span> code, <span style="color: #003399;">String</span> message,
            <span style="color: #003399;">Throwable</span> exception<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000000; font-weight: bold;">return</span> <span style="color: #000000; font-weight: bold;">new</span> Status<span style="color: #009900;">&#40;</span>severity, <span style="color: #003399;">Activator</span>.<span style="color: #006633;">PLUGIN_ID</span>, code, message,
                        exception<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000066; font-weight: bold;">void</span> log<span style="color: #009900;">&#40;</span>IStatus status<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        ILog log <span style="color: #339933;">=</span> <span style="color: #003399;">Activator</span>.<span style="color: #006633;">getDefault</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>.<span style="color: #006633;">getLog</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        log.<span style="color: #006633;">log</span><span style="color: #009900;">&#40;</span>status<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>本文是本博客原创文章，您可以自由转载，但转载请注明来源。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/v1_Wap_e1Ho" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/07/13/eclipse-rcp-plugin-log/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/07/13/eclipse-rcp-plugin-log/</feedburner:origLink></item>
		<item>
		<title>[转]卡扎菲爱他的人民，但是……</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/pexBOUzQ5Qk/</link>
		<comments>http://www.zhlwish.com/2011/05/30/%e5%8d%a1%e6%89%8e%e8%8f%b2%e7%88%b1%e4%bb%96%e7%9a%84%e4%ba%ba%e6%b0%91/#comments</comments>
		<pubDate>Mon, 30 May 2011 02:39:24 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[生活感悟]]></category>
		<category><![CDATA[民主]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=414</guid>
		<description><![CDATA[很受启发的一篇文章，作者：天则经济研究所 茅于轼 卡扎菲很爱他的人民，这是毫无疑问的。他把国家石油收入的大部分用于百姓的福利。全国百姓都享受免费医疗，甚至出国看病的费用也能报销，而且住房不要钱。百姓生活得很满足，而且一年比一年好。他爱百姓，可是百姓不领情，还要造他的反。卡扎菲百思不得其解。最后他找到的答案是西方国家在幕后煽动，否则这事绝不可能发生。 这是一切独裁者的共同思维方式。他们不但把政府的收入大部分用于百姓的福利，而且昼夜操心，为百姓谋幸福，为捍卫国家的主权独立而奋斗，还为百姓之间的纠纷主持公道。他们如此关心百姓，理应受到百姓的爱戴。现在百姓忽然要造反，对他们来讲非常不可思议。现在的独裁者并不是只顾个人享受的帝王将相，他们不是低级趣味的人，而是有理想的人，是负责任的人。当然他们也不是理想的君子，思想很复杂。但是他们的确是为人民服务的。卡扎菲很有把握地说，他受到人们的拥护和爱戴。这是他的真心话。他这样忠心耿耿为人民，现在人们反而造起反来了，他完全无法接受。最后他判断完全是西方敌对势力的所作所为。外面人往往以为，说造反派是受了境外敌对势力的煽动，完全是无中生有，是故意歪曲，恶意栽赃。其实并非如此，独裁者不是故意栽赃，他们真是这样想的。不光是卡扎菲，大多数的独裁者都是这样想问题的，因为找不到别的理由。可是他们得出了远离实际的答案。造反是完全自发的，和外国人无关。 正因为卡扎菲深信人民是爱他的，所以当有人反对他时他对这些忘恩负义的人格外痛恨，必欲除之而后快。所以手段特别狠毒，不惜下毒手杀人。不光是卡扎菲如此，一切独裁者对待民间的反政府力量都如此。他们认为杀掉的都是坏人，至少也是不知好歹的被坏人利用的人，所以毫不手软。 这是值得我们深思的问题，为什么为人民服务而得不到好报？为什么民间反政府人士认为自己是从事正义和高尚的事业，而独裁者认为这些人是忘恩负义，无理取闹，或被人利用。 我认为这里的原因是统治者对国家治理性质的误解。他们不懂得，正如我国宪法上写的“一切权力属于人民（宪法总纲第二条）”，人民才是国家的主人。统治者只不过是受人民委托临时管理国家的。卡扎菲不懂得，石油本来不属于他的，而属于全体人民的。他无权决定石油收入该如何分配。之所谓给百姓的恩施本来就是人民应该得到的。他未经百姓同意而私自占有的那部分实际上是贪污了百姓的财产。这样的认识和卡扎菲的认识完全是对立的。判断的绝然相对立，焉能不发生冲突。 统治者更不懂得人与人平等的人权观念，自以为统治者高人一等，百姓只能听他摆布，不许可有任何自由平等的想法。如果想要和统治者平起平坐，那就是大逆不道。尤其是绝不允许百姓选择别的统治者，铁打的江山要千秋万代传下去。自己死了由儿子接班。从秦始皇开始，天下的独裁者无一例外。 统治者的野心越来越大，不但不许百姓越轨行动，连类似的想法都是绝对不容许的。所以在这些国家里都关押着良心犯。他们并非存心反政府，只是要求自由平等。可是独裁者决不允许任何人和自己有平等地位，他们把自己塑造成超人的形象，是真理的发现者甚至能够创造真理，是真理的化身。他们的话就是教科书，一开口就是百姓学习的材料，而且他们的讲话就是法律。毛泽东有红宝书，卡扎菲有绿宝书，都是教百姓如何做人的。他们进而想统治百姓的思想，防止妖言惑众，搞出版审查制。于是和百姓的冲突越来越频繁，不知不觉变成了广泛的社会冲突。中国古代的皇帝都认为天下都是自己的，每一寸土地他都有权支配，任何一个老百姓他都有权指挥。现代的独裁者也这样想问题。 百姓起来造反，在独裁者看来是破坏国家安定，绝对不利于国家和百姓，要把他们消灭于萌芽状态。但是消灭不了，形势越来越严重。于是维稳压倒一切，别的统统都被压倒了。法律的尊严，社会的正义，都得让位于稳定。社会的扭曲越来越严重，维稳越来越困难，倾全国之力还觉得不够。维稳以百姓为对象，有庞大的队伍，充足的预算（来自于百姓的纳税）。这些人拿了政府的待遇，当然要为政府做事。首先是寻找可疑的敌人，结果把本来不是敌人的人也看做可疑分子，限制他们的自由。维稳到此不但没稳定，反而增加了敌对情绪。弄得风声鹤唳，手忙脚乱。结果就是进一步增加维稳的力量和经费，增加维稳的人员，形成正反馈，越搞越紧张。政府靠自我绕不出去，陷入恶性循环。 独裁者始终不明白，现在百姓要的主要不是生活福利，而是平等自由。利比亚人民生活并不差，他们缺的是人权。也有些学者认为利比亚动乱是地缘政治造成的。所谓地缘政治就是各大强国在当地瓜分势力范围。这一说法非常牵强附会。参与游行的百姓根本不懂什么地缘政治。他们自觉参与到游行队伍中，是因为自身的感受，是因为人权得不到保障。参与游行也不是因为生活问题。中国人改革以来的生活改善，其速度超过世界上任何一个别的国家。现在中国政府以为改善民生可以缓解社会矛盾，所以下一个五年规划以民生为重点，而忽视政治改革。这样一条路很可能是看错了方向。 独裁者还把国家看得至高无上，因为他们代表着国家。国家至高无上，其实就是他们自己至高无上。至于百姓，那是无所谓的。所以在他们的眼里主权高于人权。为了主权可以牺牲人权。国家如果受威胁，必要时可以无视人权。这次利比亚动乱，国家受到威胁。这个威胁来自反对派的百姓。为了消除对国家的威胁，可以消灭参与动乱的分子。所以卡扎菲动用军队杀死参与反政府活动的百姓，从而引起国际干涉，联合国通过决议在利比亚设禁飞区。禁飞区显然侵犯了国家的主权。为了保护人权，国际社会有权这样做。其理由就是人权高于主权。国家的主权之所以重要，因为它可以保护人权，抵抗外来的侵犯。反过来，如果这个主权自己就侵犯人权，要这样的主权有什么用。 在卡扎菲的眼中，联合国设禁飞区的决定正是西方在背后煽动的证据。西方国家先是煽动百姓造反，最后亲自出马干涉内政。拿这一点来看，卡扎菲是有道理的。人权思想，自由平等思想都渊源于西方。抵制西方思想的侵袭是许多东方国家领导人的目标。现在世界上的独裁国家都不在西方，都在逐渐西化的东方国家里。于是意识形态的冲突在所难免。可是最近发生在伊斯兰国家里一连串的事件说明，人权思想的确是普世价值。不论东方西方，也不论是什么宗教信仰都认可人权。这是大势所趋，不可阻挡。连中国也不得不对设置禁飞区投了弃权票。因为否认人权，把主权看得高于一切，为了主权国家有权屠杀百姓，实在是说不过去的。不过在中国几千年的皇权历史中，任何反对皇权的人都要被灭三族，杀个精光。现在跟随世界潮流，这种认识已经基本上被否定。这是我们政治上的巨大进步。 利比亚的事态还在发展中，结果如何还很难说。追求人权未必能够得到人权。搞得不好反而会破坏人权。如果利比亚陷入内战，双方都说为人权而战，长期流血冲突，国家陷于分裂，最遭殃的就是百姓。如何避免这种结果，双方都要有妥协和让步的思想准备。要真正把人民的利益放在最重要的位置上来考虑，党派的利益要退居人民利益之后。可惜的是理性往往不能战胜情绪，事情的发展不以人们的意志为转移。国家被拖入对一切人都不利的状态也完全有可能。]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/rMmyc5hgQwls3-VGtuvdIFP3xl8/0/da"><img src="http://feedads.g.doubleclick.net/~a/rMmyc5hgQwls3-VGtuvdIFP3xl8/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/rMmyc5hgQwls3-VGtuvdIFP3xl8/1/da"><img src="http://feedads.g.doubleclick.net/~a/rMmyc5hgQwls3-VGtuvdIFP3xl8/1/di" border="0" ismap="true"></img></a></p><p>很受启发的一篇文章，作者：天则经济研究所   茅于轼</p>
<p>卡扎菲很爱他的人民，这是毫无疑问的。他把国家石油收入的大部分用于百姓的福利。全国百姓都享受免费医疗，甚至出国看病的费用也能报销，而且住房不要钱。百姓生活得很满足，而且一年比一年好。他爱百姓，可是百姓不领情，还要造他的反。卡扎菲百思不得其解。最后他找到的答案是西方国家在幕后煽动，否则这事绝不可能发生。</p>
<p>这是一切独裁者的共同思维方式。他们不但把政府的收入大部分用于百姓的福利，而且昼夜操心，为百姓谋幸福，为捍卫国家的主权独立而奋斗，还为百姓之间的纠纷主持公道。他们如此关心百姓，理应受到百姓的爱戴。现在百姓忽然要造反，对他们来讲非常不可思议。现在的独裁者并不是只顾个人享受的帝王将相，他们不是低级趣味的人，而是有理想的人，是负责任的人。当然他们也不是理想的君子，思想很复杂。但是他们的确是为人民服务的。卡扎菲很有把握地说，他受到人们的拥护和爱戴。这是他的真心话。他这样忠心耿耿为人民，现在人们反而造起反来了，他完全无法接受。最后他判断完全是西方敌对势力的所作所为。外面人往往以为，说造反派是受了境外敌对势力的煽动，完全是无中生有，是故意歪曲，恶意栽赃。其实并非如此，独裁者不是故意栽赃，他们真是这样想的。不光是卡扎菲，大多数的独裁者都是这样想问题的，因为找不到别的理由。可是他们得出了远离实际的答案。造反是完全自发的，和外国人无关。</p>
<p><span id="more-414"></span></p>
<p>正因为卡扎菲深信人民是爱他的，所以当有人反对他时他对这些忘恩负义的人格外痛恨，必欲除之而后快。所以手段特别狠毒，不惜下毒手杀人。不光是卡扎菲如此，一切独裁者对待民间的反政府力量都如此。他们认为杀掉的都是坏人，至少也是不知好歹的被坏人利用的人，所以毫不手软。</p>
<p>这是值得我们深思的问题，为什么为人民服务而得不到好报？为什么民间反政府人士认为自己是从事正义和高尚的事业，而独裁者认为这些人是忘恩负义，无理取闹，或被人利用。</p>
<p>我认为这里的原因是统治者对国家治理性质的误解。他们不懂得，正如我国宪法上写的“一切权力属于人民（宪法总纲第二条）”，人民才是国家的主人。统治者只不过是受人民委托临时管理国家的。卡扎菲不懂得，石油本来不属于他的，而属于全体人民的。他无权决定石油收入该如何分配。之所谓给百姓的恩施本来就是人民应该得到的。他未经百姓同意而私自占有的那部分实际上是贪污了百姓的财产。这样的认识和卡扎菲的认识完全是对立的。判断的绝然相对立，焉能不发生冲突。</p>
<p>统治者更不懂得人与人平等的人权观念，自以为统治者高人一等，百姓只能听他摆布，不许可有任何自由平等的想法。如果想要和统治者平起平坐，那就是大逆不道。尤其是绝不允许百姓选择别的统治者，铁打的江山要千秋万代传下去。自己死了由儿子接班。从秦始皇开始，天下的独裁者无一例外。</p>
<p>统治者的野心越来越大，不但不许百姓越轨行动，连类似的想法都是绝对不容许的。所以在这些国家里都关押着良心犯。他们并非存心反政府，只是要求自由平等。可是独裁者决不允许任何人和自己有平等地位，他们把自己塑造成超人的形象，是真理的发现者甚至能够创造真理，是真理的化身。他们的话就是教科书，一开口就是百姓学习的材料，而且他们的讲话就是法律。毛泽东有红宝书，卡扎菲有绿宝书，都是教百姓如何做人的。他们进而想统治百姓的思想，防止妖言惑众，搞出版审查制。于是和百姓的冲突越来越频繁，不知不觉变成了广泛的社会冲突。中国古代的皇帝都认为天下都是自己的，每一寸土地他都有权支配，任何一个老百姓他都有权指挥。现代的独裁者也这样想问题。</p>
<p>百姓起来造反，在独裁者看来是破坏国家安定，绝对不利于国家和百姓，要把他们消灭于萌芽状态。但是消灭不了，形势越来越严重。于是维稳压倒一切，别的统统都被压倒了。法律的尊严，社会的正义，都得让位于稳定。社会的扭曲越来越严重，维稳越来越困难，倾全国之力还觉得不够。维稳以百姓为对象，有庞大的队伍，充足的预算（来自于百姓的纳税）。这些人拿了政府的待遇，当然要为政府做事。首先是寻找可疑的敌人，结果把本来不是敌人的人也看做可疑分子，限制他们的自由。维稳到此不但没稳定，反而增加了敌对情绪。弄得风声鹤唳，手忙脚乱。结果就是进一步增加维稳的力量和经费，增加维稳的人员，形成正反馈，越搞越紧张。政府靠自我绕不出去，陷入恶性循环。 </p>
<p>独裁者始终不明白，现在百姓要的主要不是生活福利，而是平等自由。利比亚人民生活并不差，他们缺的是人权。也有些学者认为利比亚动乱是地缘政治造成的。所谓地缘政治就是各大强国在当地瓜分势力范围。这一说法非常牵强附会。参与游行的百姓根本不懂什么地缘政治。他们自觉参与到游行队伍中，是因为自身的感受，是因为人权得不到保障。参与游行也不是因为生活问题。中国人改革以来的生活改善，其速度超过世界上任何一个别的国家。现在中国政府以为改善民生可以缓解社会矛盾，所以下一个五年规划以民生为重点，而忽视政治改革。这样一条路很可能是看错了方向。</p>
<p>独裁者还把国家看得至高无上，因为他们代表着国家。国家至高无上，其实就是他们自己至高无上。至于百姓，那是无所谓的。所以在他们的眼里主权高于人权。为了主权可以牺牲人权。国家如果受威胁，必要时可以无视人权。这次利比亚动乱，国家受到威胁。这个威胁来自反对派的百姓。为了消除对国家的威胁，可以消灭参与动乱的分子。所以卡扎菲动用军队杀死参与反政府活动的百姓，从而引起国际干涉，联合国通过决议在利比亚设禁飞区。禁飞区显然侵犯了国家的主权。为了保护人权，国际社会有权这样做。其理由就是人权高于主权。国家的主权之所以重要，因为它可以保护人权，抵抗外来的侵犯。反过来，如果这个主权自己就侵犯人权，要这样的主权有什么用。</p>
<p>在卡扎菲的眼中，联合国设禁飞区的决定正是西方在背后煽动的证据。西方国家先是煽动百姓造反，最后亲自出马干涉内政。拿这一点来看，卡扎菲是有道理的。人权思想，自由平等思想都渊源于西方。抵制西方思想的侵袭是许多东方国家领导人的目标。现在世界上的独裁国家都不在西方，都在逐渐西化的东方国家里。于是意识形态的冲突在所难免。可是最近发生在伊斯兰国家里一连串的事件说明，人权思想的确是普世价值。不论东方西方，也不论是什么宗教信仰都认可人权。这是大势所趋，不可阻挡。连中国也不得不对设置禁飞区投了弃权票。因为否认人权，把主权看得高于一切，为了主权国家有权屠杀百姓，实在是说不过去的。不过在中国几千年的皇权历史中，任何反对皇权的人都要被灭三族，杀个精光。现在跟随世界潮流，这种认识已经基本上被否定。这是我们政治上的巨大进步。</p>
<p>利比亚的事态还在发展中，结果如何还很难说。追求人权未必能够得到人权。搞得不好反而会破坏人权。如果利比亚陷入内战，双方都说为人权而战，长期流血冲突，国家陷于分裂，最遭殃的就是百姓。如何避免这种结果，双方都要有妥协和让步的思想准备。要真正把人民的利益放在最重要的位置上来考虑，党派的利益要退居人民利益之后。可惜的是理性往往不能战胜情绪，事情的发展不以人们的意志为转移。国家被拖入对一切人都不利的状态也完全有可能。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/pexBOUzQ5Qk" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/05/30/%e5%8d%a1%e6%89%8e%e8%8f%b2%e7%88%b1%e4%bb%96%e7%9a%84%e4%ba%ba%e6%b0%91/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/05/30/%e5%8d%a1%e6%89%8e%e8%8f%b2%e7%88%b1%e4%bb%96%e7%9a%84%e4%ba%ba%e6%b0%91/</feedburner:origLink></item>
		<item>
		<title>Ubuntu开机自动启动GAppProxy</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/sryUk4ulJig/</link>
		<comments>http://www.zhlwish.com/2011/05/16/ubuntu%e5%bc%80%e6%9c%ba%e8%87%aa%e5%8a%a8%e5%90%af%e5%8a%a8gappproxy/#comments</comments>
		<pubDate>Mon, 16 May 2011 09:06:42 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>
		<category><![CDATA[google app engine]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[ubuntu]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=412</guid>
		<description><![CDATA[最近Gmail总是时断时续，实在是受不了，只能/翻/墙/，我真得被逼的，尼玛！ GAppProxy + Firefox + AutoProxy是不可多得的/翻/墙/利器，对一般的用户来讲虽然设置起来还是比较麻烦的，不过对于俺们程序猿来讲这个都不会弄就不用做程序猿：http://code.google.com/p/gappproxy/wiki/GAppProxy_2_0_0_Manual。 在Ubuntu上，每次启动都需要在Terminal里面执行python proxy.py就可以运行，不过需要一直开着Terminal，这个很不爽，而且每次都需要执行两条命令（一条cd，一条python），比较麻烦。 于是尝试了一下，开机自动启动GAppProxy的办法如下： 1. 用VIM打开~/.profile vim ~/.profile 2. 在最后加上： cd /opt/gappproxy/localproxy nohup python proxy.py &#38; cd ~ 注意，在最后要加上&#038;哟 nohup是表示关掉shell后不关闭在后台执行的程序。]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/nLmgy_MfQuwQay5iWVVRSIvOw8I/0/da"><img src="http://feedads.g.doubleclick.net/~a/nLmgy_MfQuwQay5iWVVRSIvOw8I/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/nLmgy_MfQuwQay5iWVVRSIvOw8I/1/da"><img src="http://feedads.g.doubleclick.net/~a/nLmgy_MfQuwQay5iWVVRSIvOw8I/1/di" border="0" ismap="true"></img></a></p><p>最近Gmail总是时断时续，实在是受不了，只能/翻/墙/，我真得被逼的，尼玛！</p>
<p>GAppProxy + Firefox + AutoProxy是不可多得的/翻/墙/利器，对一般的用户来讲虽然设置起来还是比较麻烦的，不过对于俺们程序猿来讲这个都不会弄就不用做程序猿：<a href="http://code.google.com/p/gappproxy/wiki/GAppProxy_2_0_0_Manual">http://code.google.com/p/gappproxy/wiki/GAppProxy_2_0_0_Manual</a>。</p>
<p>在Ubuntu上，每次启动都需要在Terminal里面执行python proxy.py就可以运行，不过需要一直开着Terminal，这个很不爽，而且每次都需要执行两条命令（一条cd，一条python），比较麻烦。</p>
<p>于是尝试了一下，开机自动启动GAppProxy的办法如下：<br />
<span id="more-412"></span><br />
1. 用VIM打开~/.profile</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:Verdana,Courier New;"><span style="color: #c20cb9; font-weight: bold;">vim</span> ~<span style="color: #000000; font-weight: bold;">/</span>.profile</pre></div></div>

<p>2. 在最后加上：</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:Verdana,Courier New;"><span style="color: #7a0874; font-weight: bold;">cd</span> <span style="color: #000000; font-weight: bold;">/</span>opt<span style="color: #000000; font-weight: bold;">/</span>gappproxy<span style="color: #000000; font-weight: bold;">/</span>localproxy
<span style="color: #c20cb9; font-weight: bold;">nohup</span> python proxy.py  <span style="color: #000000; font-weight: bold;">&amp;</span>
<span style="color: #7a0874; font-weight: bold;">cd</span> ~</pre></div></div>

<p>注意，在最后要加上&#038;哟<br />
nohup是表示关掉shell后不关闭在后台执行的程序。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/sryUk4ulJig" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/05/16/ubuntu%e5%bc%80%e6%9c%ba%e8%87%aa%e5%8a%a8%e5%90%af%e5%8a%a8gappproxy/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/05/16/ubuntu%e5%bc%80%e6%9c%ba%e8%87%aa%e5%8a%a8%e5%90%af%e5%8a%a8gappproxy/</feedburner:origLink></item>
		<item>
		<title>解决Ubuntu上Chrome死掉</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/W_RQHwzrQYQ/</link>
		<comments>http://www.zhlwish.com/2011/05/13/chrome_stop_on_ubuntu/#comments</comments>
		<pubDate>Fri, 13 May 2011 01:14:59 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>
		<category><![CDATA[chrome]]></category>
		<category><![CDATA[lunux]]></category>
		<category><![CDATA[ubuntu]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=399</guid>
		<description><![CDATA[为什么会出现这样的问题不清楚，只能祭出终极解决办法，重装Chrome。 sudo apt-get remove chromium-browser sudo apt-get install chromium-browser 重装之后问题依旧，想想配置文件没有删掉吧，可能是这个问题，Chrome的配置文件位置：~/.config/chromium，删掉即可 sudo apt-get remove chromium-browser rm -rf ~/.config/chromium sudo apt-get install chromium-browser]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/snJxRDreNEh9PuVzDVmCL1pDEQs/0/da"><img src="http://feedads.g.doubleclick.net/~a/snJxRDreNEh9PuVzDVmCL1pDEQs/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/snJxRDreNEh9PuVzDVmCL1pDEQs/1/da"><img src="http://feedads.g.doubleclick.net/~a/snJxRDreNEh9PuVzDVmCL1pDEQs/1/di" border="0" ismap="true"></img></a></p><p>为什么会出现这样的问题不清楚，只能祭出终极解决办法，重装Chrome。</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:Verdana,Courier New;"><span style="color: #c20cb9; font-weight: bold;">sudo</span> <span style="color: #c20cb9; font-weight: bold;">apt-get</span> remove chromium-browser
<span style="color: #c20cb9; font-weight: bold;">sudo</span> <span style="color: #c20cb9; font-weight: bold;">apt-get</span> <span style="color: #c20cb9; font-weight: bold;">install</span> chromium-browser</pre></div></div>

<p>重装之后问题依旧，想想配置文件没有删掉吧，可能是这个问题，Chrome的配置文件位置：~/.config/chromium，删掉即可</p>
<p><span id="more-399"></span></p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:Verdana,Courier New;"><span style="color: #c20cb9; font-weight: bold;">sudo</span> <span style="color: #c20cb9; font-weight: bold;">apt-get</span> remove chromium-browser
<span style="color: #c20cb9; font-weight: bold;">rm</span> <span style="color: #660033;">-rf</span> ~<span style="color: #000000; font-weight: bold;">/</span>.config<span style="color: #000000; font-weight: bold;">/</span>chromium
<span style="color: #c20cb9; font-weight: bold;">sudo</span> <span style="color: #c20cb9; font-weight: bold;">apt-get</span> <span style="color: #c20cb9; font-weight: bold;">install</span> chromium-browser</pre></div></div>

<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/W_RQHwzrQYQ" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/05/13/chrome_stop_on_ubuntu/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/05/13/chrome_stop_on_ubuntu/</feedburner:origLink></item>
		<item>
		<title>在Ubuntu的右键菜单中添加“Open Terminal Here / Open in Terminal”</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/4Qprlh_AsHQ/</link>
		<comments>http://www.zhlwish.com/2011/04/22/ubuntu-open-terminal-here-open-in-terminal/#comments</comments>
		<pubDate>Fri, 22 Apr 2011 09:13:28 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>
		<category><![CDATA[gnome]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[ubuntu]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=376</guid>
		<description><![CDATA[Ubuntu默认使用GNOME作为桌面环境，Nautilus是GNOME下默认的文件浏览器，我想在Nautilus的右键菜单中添加“Open Terminal Here“或者”Open in Terminal“这样的菜单，在文件浏览器中直接点击右键菜单即可在打开Terminal并且cd到当前目录。 nautilus-open-terminal是Nautilus的一个扩展，可以达到前文描述的功能。 安装如下： sudo apt-get install nautilus-open-terminal 安装完成后，有人说需要重启电脑，其实不用，只需要kill掉进程，然后打开文件浏览器nautilus就可以了 killall -9 nautilus 参考： open terminal here nautilus-open-terminal : terminal quick launch How to open a menu with &#8216;Open Terminal Here&#8217; in Ubuntu 10.04 by left clicking desktop, &#8230; <a href="http://www.zhlwish.com/2011/04/22/ubuntu-open-terminal-here-open-in-terminal/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/UgCEBeqn1o-3W6kpzchcrv4x2P4/0/da"><img src="http://feedads.g.doubleclick.net/~a/UgCEBeqn1o-3W6kpzchcrv4x2P4/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/UgCEBeqn1o-3W6kpzchcrv4x2P4/1/da"><img src="http://feedads.g.doubleclick.net/~a/UgCEBeqn1o-3W6kpzchcrv4x2P4/1/di" border="0" ismap="true"></img></a></p><p>Ubuntu默认使用GNOME作为桌面环境，Nautilus是GNOME下默认的文件浏览器，我想在Nautilus的右键菜单中添加“Open Terminal Here“或者”Open in Terminal“这样的菜单，在文件浏览器中直接点击右键菜单即可在打开Terminal并且cd到当前目录。</p>
<p>nautilus-open-terminal是Nautilus的一个扩展，可以达到前文描述的功能。<br />
<span id="more-376"></span><br />
安装如下：</p>
<pre>sudo apt-get install nautilus-open-terminal</pre>
<p>安装完成后，有人说需要重启电脑，其实不用，只需要kill掉进程，然后打开文件浏览器nautilus就可以了</p>
<pre>killall -9 nautilus</pre>
<p>参考：</p>
<ul>
<li><a href="http://ubuntuforums.org/showthread.php?t=459899">open terminal here</a></li>
<li><a href="http://ubuntu-tutorials.com/2007/05/13/nautilus-open-terminal-terminal-quick-launch/">nautilus-open-terminal : terminal quick launch</a></li>
<li><a href="http://superuser.com/questions/166407/how-to-open-a-menu-with-open-terminal-here-in-ubuntu-10-04-by-left-clicking-des">How to open a menu with &#8216;Open Terminal Here&#8217; in Ubuntu 10.04 by left clicking desktop, or inside folder?</a></li>
<li><a href="http://fanqiang.chinaunix.net/a1/b5/20010920/0700001319.html">中文man手册:killall &#8211; 以名字方式来杀死进程</a></li>
<li><a href="http://hi.baidu.com/hy0kl/blog/item/c8bfee396a2a6af83a87cec7.html">kill 参数中信号名</a></li>
</ul>
<div>本文是本博客原创文章，您可以自由转载，但转载请注明来源。</div>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/4Qprlh_AsHQ" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/04/22/ubuntu-open-terminal-here-open-in-terminal/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/04/22/ubuntu-open-terminal-here-open-in-terminal/</feedburner:origLink></item>
		<item>
		<title>Bash Shell快捷键</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/PJj0F5XSIsM/</link>
		<comments>http://www.zhlwish.com/2011/04/11/bash-shell%e5%bf%ab%e6%8d%b7%e9%94%ae/#comments</comments>
		<pubDate>Mon, 11 Apr 2011 12:49:36 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Linux技术]]></category>
		<category><![CDATA[bash]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[shell]]></category>
		<category><![CDATA[ubunut]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=368</guid>
		<description><![CDATA[原文来自这里Bash Shell Shortcuts和这里Bash Shell 快捷键的学习使用，但是归根结底，还是来自这里Bash Shell Shortcuts，我只是稍微翻译了一下，重新排了序 Ctrl系 Ctrl + a - 光标跳转到命令的开头（当命令敲完了，结果发现开头敲错了的时候用） Ctrl + e - 光标跳转到命令结尾 Ctrl + b - 光标往左移动一个字符 Ctrl + f - 光标往右移动一个字符 Ctrl + x + x - 光标移动到最后和当前位置两个地方跳转 Ctrl + d - 删除光标所在位置的字符 &#8230; <a href="http://www.zhlwish.com/2011/04/11/bash-shell%e5%bf%ab%e6%8d%b7%e9%94%ae/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/2sDiMNGckXsML5NVfKfaa5XtEXM/0/da"><img src="http://feedads.g.doubleclick.net/~a/2sDiMNGckXsML5NVfKfaa5XtEXM/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/2sDiMNGckXsML5NVfKfaa5XtEXM/1/da"><img src="http://feedads.g.doubleclick.net/~a/2sDiMNGckXsML5NVfKfaa5XtEXM/1/di" border="0" ismap="true"></img></a></p><p>原文来自这里<a href="http://linuxhelp.blogspot.com/2005/08/bash-shell-shortcuts.html">Bash Shell Shortcuts</a>和这里<a href="http://www.dbanotes.net/techmemo/shell_shortcut.html">Bash Shell 快捷键的学习使用</a>，但是归根结底，还是来自这里<a href="http://linuxhelp.blogspot.com/2005/08/bash-shell-shortcuts.html">Bash Shell Shortcuts</a>，我只是稍微翻译了一下，重新排了序<br />
<span id="more-368"></span><br />
<strong>Ctrl系</strong></p>
<pre>Ctrl + a - 光标跳转到命令的开头（当命令敲完了，结果发现开头敲错了的时候用）
Ctrl + e - 光标跳转到命令结尾
Ctrl + b - 光标往左移动一个字符
Ctrl + f - 光标往右移动一个字符
Ctrl + x + x - 光标移动到最后和当前位置两个地方跳转

Ctrl + d - 删除光标所在位置的字符
Ctrl + h - 删除光标所在位置之前的一个字符
Ctrl + k - 删除光标所在位置之后（右边）的所有字符
Ctrl + u - 删除光标所在位置之前（左边）的所有字符 （密码输入错误的时候比较有用）
Ctrl + w - 删除最后输入的单词 

Ctrl + c - 终止正在执行的命令
Ctrl + z - 挂起/停止正在执行的命令

Ctrl + l - 清屏，类似 clear 命令
Ctrl + r - 查找之前执行过的命令

Ctrl + y - 在当前光标处插入之前输入的命令 （有用）</pre>
<p><strong>Alt系</strong></p>
<pre>Alt + &lt; - 显示历史命令中的第一条 （咱中文用户就不用试了，和输入法切换冲突）
Alt + &gt; - 显示历史命中中的最后一条
Alt + ? - 显示命令不全的候选项
Alt + * - 插入命令不全的所有候选项
Alt + / - 补全文件（夹）名称
Alt + . - 插入前一个命令的最后一个参数 （这个很好很强大）
Alt + b - 光标往左移动一个单词
Alt + f - 光标往右移动一个单词（诶，和显示菜单的快捷键冲突了）
Alt + c - 将光标所在的字符变成大写
Alt + d - 删除光标所在位置的单词

Alt + l - 将单词中光标位置之后的字符变成大写
Alt + u - 将单词中光标位置之后的字符变成大写
Alt + t - 在单词中的字符间跳转（诶，和菜单的快捷键冲突了）

Alt + y - 在当前光标处插入<strong>之前</strong><em>之前</em>（两个之前，不是我敲错了）输入的命令（请和Ctrl + y比较）

Alt + back-space - 删除光标所在位置之前（左边）的所有字符</pre>
<p><strong>其他特定的键绑定</strong><br />
输入 bind -P 可以查看所有的键盘绑定。这一系列我觉得更为实用。<br />
<strong><em>下面的命令中2T表示按两下Tab键</em><br />
</strong></p>
<pre>$ 2T - 命令行补全，显示所有候选项
$ (string)2T - 命令行补全，显示以string开头的所有候选项
$ /2T - 显示文件夹中的所有文件，包括.开头的隐藏文件
$ ./2T - 显示文件夹的子文件夹，包括.开头的隐藏文件
$ *2T - 显示文件夹的子文件夹，不包括.开头的隐藏文件
$ ~2T - 显示"/etc/passwd"vs中所有的用户？ （不是很明白这个是干什么用的）
$ $2T - 所有的系统变量
$ @2T - "/etc/hosts"中的所有的项 （依然不明白）
$ =2T - 和ls或者dir输出的一样 （更不明白有了ls，还要这个干嘛，Tab控）

Esc + T - 交换光标前面的两个单词 （这个好玩）</pre>
<p>有些不实用的被我直接删掉了，如果需要找的话，参考<a href="http://www.bigsmoke.us/readline/shortcuts">Readline shortcuts</a>这个把，里面居然有简单的图示。</p>
<p>本文是本博客原创文章，您可以自由转载，但转载请注明来源。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/PJj0F5XSIsM" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/04/11/bash-shell%e5%bf%ab%e6%8d%b7%e9%94%ae/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/04/11/bash-shell%e5%bf%ab%e6%8d%b7%e9%94%ae/</feedburner:origLink></item>
		<item>
		<title>使用PyXMPP向GTalk发送消息</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/NPkOWX_zjaM/</link>
		<comments>http://www.zhlwish.com/2011/04/04/pyxmpp_gtalk/#comments</comments>
		<pubDate>Mon, 04 Apr 2011 07:04:40 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Python]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=339</guid>
		<description><![CDATA[2011年9月23日16:30:54 更新 关于JID，请参考XMPP中资源/Resource的解释和JID Python有2个package实现了XMPP和Jabber标准：xmpppy和 pyxmpp，哪个好就自然是一个问题。一般公认的看法是pyxmpp是首选，它完全符合XMPP协议，开发也保持活跃的状态，并且最新的版本是2010年发布的。而xmpppy则公认为设计上有不太合理之处，也不完全符合XMPP协议，所以不推荐使用，而且还是在2009年4月份更新的，开源神马的最怕不更新了！ 安装 在Ubuntu 10.10上安装pyxmpp有两种办法，一种是一步到位： sudo apt-get install python-pyxmpp 另一种是自己下载，之后安装，但是由于pyxmpp依赖python-libxml2，python-dnspython，而且在用gtalk发送消息时使用tls加密，因而还依赖python-m2crypto，所以安装过程如下： sudo apt-get install python-libxml2 sudo apt-get install python-dnspython sudo apt-get install python-m2crypto tar -xzvf pyxmpp-1.1.1.tar.gz cd pyxmpp-1.1.1 sudo python configure.py sudo python setup.py build sudo python setup.py &#8230; <a href="http://www.zhlwish.com/2011/04/04/pyxmpp_gtalk/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/gWM7dZe1Yxnl8cmSYs2ZESu7QIM/0/da"><img src="http://feedads.g.doubleclick.net/~a/gWM7dZe1Yxnl8cmSYs2ZESu7QIM/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/gWM7dZe1Yxnl8cmSYs2ZESu7QIM/1/da"><img src="http://feedads.g.doubleclick.net/~a/gWM7dZe1Yxnl8cmSYs2ZESu7QIM/1/di" border="0" ismap="true"></img></a></p><p>2011年9月23日16:30:54 更新</p>
<p>关于JID，请参考<a href="http://www.zhlwish.com/2011/09/23/xmpp_resource_jid/" title="XMPP中资源/Resource的解释和JID" target="_blank">XMPP中资源/Resource的解释和JID</a></p>
<hr />
<p>Python有2个package实现了XMPP和Jabber标准：<a href="http://xmpppy.sourceforge.net/">xmpppy</a>和 <a href="http://pyxmpp.jajcus.net/">pyxmpp</a>，哪个好就自然是一个问题。一般公认的看法是<a href="http://pyxmpp.jajcus.net/">pyxmpp</a>是首选，它完全符合XMPP协议，开发也保持活跃的状态，并且最新的版本是2010年发布的。而<a href="http://xmpppy.sourceforge.net/">xmpppy</a>则公认为设计上有不太合理之处，也不完全符合XMPP协议，所以不推荐使用，而且还是在2009年4月份更新的，开源神马的最怕不更新了！<br />
<span id="more-339"></span><br />
<strong>安装</strong></p>
<p>在Ubuntu 10.10上安装pyxmpp有两种办法，一种是一步到位：</p>
<pre>sudo apt-get install python-pyxmpp</pre>
<p>另一种是自己下载，之后安装，但是由于pyxmpp依赖python-libxml2，python-dnspython，而且在用gtalk发送消息时使用tls加密，因而还依赖python-m2crypto，所以安装过程如下：</p>
<pre>sudo apt-get install python-libxml2
sudo apt-get install python-dnspython
sudo apt-get install python-m2crypto

tar -xzvf pyxmpp-1.1.1.tar.gz
cd pyxmpp-1.1.1
sudo python configure.py
sudo python setup.py build
sudo python setup.py install</pre>
<p><strong>代码</strong></p>
<p>环境就安装好了，下面是代码：</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:Verdana,Courier New;"><span style="color: #808080; font-style: italic;">#!/usr/bin/python</span>
<span style="color: #808080; font-style: italic;"># -*- coding: utf-8 -*-</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">from</span> pyxmpp.<span style="color: black;">jid</span> <span style="color: #ff7700;font-weight:bold;">import</span> JID
<span style="color: #ff7700;font-weight:bold;">from</span> pyxmpp.<span style="color: black;">message</span> <span style="color: #ff7700;font-weight:bold;">import</span> Message
<span style="color: #ff7700;font-weight:bold;">from</span> pyxmpp.<span style="color: black;">jabber</span>.<span style="color: black;">client</span> <span style="color: #ff7700;font-weight:bold;">import</span> JabberClient
<span style="color: #ff7700;font-weight:bold;">from</span> pyxmpp.<span style="color: black;">jabber</span>.<span style="color: black;">simple</span> <span style="color: #ff7700;font-weight:bold;">import</span> send_message
<span style="color: #ff7700;font-weight:bold;">from</span> pyxmpp <span style="color: #ff7700;font-weight:bold;">import</span> streamtls
&nbsp;
<span style="color: #ff7700;font-weight:bold;">class</span> Gtalk<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>:
    <span style="color: #ff7700;font-weight:bold;">def</span> <span style="color: #0000cd;">__init__</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span>, sid, spwd<span style="color: black;">&#41;</span>:
        <span style="color: #008000;">self</span>.<span style="color: black;">sid</span> = JID<span style="color: black;">&#40;</span>sid<span style="color: black;">&#41;</span>
        <span style="color: #008000;">self</span>.<span style="color: black;">spwd</span> = spwd
&nbsp;
    <span style="color: #ff7700;font-weight:bold;">def</span> send_msg<span style="color: black;">&#40;</span><span style="color: #008000;">self</span>, rid,  msg<span style="color: black;">&#41;</span>:
        <span style="color: #008000;">self</span>.<span style="color: black;">rid</span> = JID<span style="color: black;">&#40;</span>rid<span style="color: black;">&#41;</span>
        <span style="color: #ff7700;font-weight:bold;">if</span> <span style="color: #ff7700;font-weight:bold;">not</span> <span style="color: #008000;">self</span>.<span style="color: black;">sid</span>.<span style="color: #dc143c;">resource</span>:
            <span style="color: #008000;">self</span>.<span style="color: black;">sid</span> = JID<span style="color: black;">&#40;</span><span style="color: #008000;">self</span>.<span style="color: black;">sid</span>.<span style="color: black;">node</span>, <span style="color: #008000;">self</span>.<span style="color: black;">sid</span>.<span style="color: black;">domain</span>, <span style="color: #483d8b;">'send_message'</span><span style="color: black;">&#41;</span>
&nbsp;
        msg = Message<span style="color: black;">&#40;</span>to_jid=<span style="color: #008000;">self</span>.<span style="color: black;">rid</span>, body=msg<span style="color: black;">&#41;</span>
        <span style="color: #ff7700;font-weight:bold;">def</span> send<span style="color: black;">&#40;</span>stream<span style="color: black;">&#41;</span>:
            stream.<span style="color: black;">send</span><span style="color: black;">&#40;</span>msg<span style="color: black;">&#41;</span>
&nbsp;
        <span style="color: #008000;">self</span>.<span style="color: black;">xmpp_do</span><span style="color: black;">&#40;</span>send<span style="color: black;">&#41;</span>
&nbsp;
    <span style="color: #ff7700;font-weight:bold;">def</span> xmpp_do<span style="color: black;">&#40;</span><span style="color: #008000;">self</span>, function<span style="color: black;">&#41;</span>:
        <span style="color: #ff7700;font-weight:bold;">class</span> Client<span style="color: black;">&#40;</span>JabberClient<span style="color: black;">&#41;</span>:
            <span style="color: #ff7700;font-weight:bold;">def</span> session_started<span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>:
                function<span style="color: black;">&#40;</span><span style="color: #008000;">self</span>.<span style="color: black;">stream</span><span style="color: black;">&#41;</span>
                <span style="color: #008000;">self</span>.<span style="color: black;">disconnect</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
&nbsp;
        tls = streamtls.<span style="color: black;">TLSSettings</span><span style="color: black;">&#40;</span>require=<span style="color: #008000;">True</span>, verify_peer=<span style="color: #008000;">False</span><span style="color: black;">&#41;</span>
        auth = <span style="color: black;">&#91;</span><span style="color: #483d8b;">'sasl:PLAIN'</span><span style="color: black;">&#93;</span>
        gtalkClient = Client<span style="color: black;">&#40;</span><span style="color: #008000;">self</span>.<span style="color: black;">sid</span>, <span style="color: #008000;">self</span>.<span style="color: black;">spwd</span>, tls_settings=tls, auth_methods=auth<span style="color: black;">&#41;</span>
        gtalkClient.<span style="color: black;">connect</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
        <span style="color: #ff7700;font-weight:bold;">try</span>:
            gtalkClient.<span style="color: black;">loop</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
        <span style="color: #ff7700;font-weight:bold;">except</span> <span style="color: #008000;">KeyboardInterrupt</span>:
            <span style="color: #ff7700;font-weight:bold;">print</span> u<span style="color: #483d8b;">'disconnecting...'</span>
            gtalkClient.<span style="color: black;">disconnect</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">if</span> __name__ == <span style="color: #483d8b;">'__main__'</span>:
    g = Gtalk<span style="color: black;">&#40;</span><span style="color: #483d8b;">'myaccount@gmail.com'</span>, u<span style="color: #483d8b;">'mypassword'</span><span style="color: black;">&#41;</span>
    g.<span style="color: black;">send_msg</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'to@gmail.com'</span>, <span style="color: #483d8b;">'message'</span><span style="color: black;">&#41;</span></pre></div></div>

<p>将其中的帐号和密码替换过来，就可以直接运行了。</p>
<p><strong>出错</strong></p>
<p>如果出现：raise FatalStreamError,”StartTLS support disabled, but required by peer 这样的错误信息，可能是没有安装Python的M2Crypto包，或者版本太老了吧。</p>
<p><strong>参考</strong></p>
<ul>
<li><a href="http://pyxmpp.jajcus.net/">PyXMPP：A Python Jabber/XMPP implementation.</a></li>
<li><a href="http://www.stillhq.com/google/gtalk/">Getting Google Talk working with PyXMPP</a></li>
</ul>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/NPkOWX_zjaM" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/04/04/pyxmpp_gtalk/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/04/04/pyxmpp_gtalk/</feedburner:origLink></item>
		<item>
		<title>CakePHP在Windows+Apache上的配置</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/pw0SHUpgB7E/</link>
		<comments>http://www.zhlwish.com/2011/03/28/cakephp_win_apache/#comments</comments>
		<pubDate>Sun, 27 Mar 2011 16:30:00 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[PHP]]></category>
		<category><![CDATA[apache]]></category>
		<category><![CDATA[cakephp]]></category>
		<category><![CDATA[mod_rewrite]]></category>
		<category><![CDATA[mvc]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=328</guid>
		<description><![CDATA[Windows上Apache+PHP+MySQL的安装配置就不多说了，这篇文章写得不错，全面实用PHP环境搭建:Windows 7下安装配置PHP+Apache+Mysql环境教程 不过我安装好PHP之后，发现Apache启动的时候总是无法加载extention，在log/error.log里面打印一句话： PHP Warning: PHP Startup: Unable to load dynamic library 后来把php的安装路径加入到系统环境变量PATH中就解决了这个问题，注意一定是系统环境变量，本人最初是傻不啦叽的加入到用户环境变量的PATH里面，结果不起作用。 经过测试PHP的环境搭建好之后，就可以开始配置CakePHP了，我下载的CakePHP解压后放在E:\Working\cakephp里面，下文多出要用到，特此声明。 首先启动Apache的mod_rewrite，在httpd.conf里面找到下面的语句，在118行左右，去掉最前的注释符号(#) #LoadModule rewrite_module modules/mod_rewrite.so 然后在httpd.conf的最后加入以下配置： Alias "/cake" "e:/Working/cakephp" &#60;Directory "e:/Working/cakephp"&#62; Options FollowSymLinks AllowOverride All Order allow,deny Allow from all &#60;/Directory&#62; 重启Apache后，访问http://localhost/cake出现”The requested URL /Working/cakephp/app/webroot/index.php was not &#8230; <a href="http://www.zhlwish.com/2011/03/28/cakephp_win_apache/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/6vFCinlQOiBkf5n-1PqGFkelbSM/0/da"><img src="http://feedads.g.doubleclick.net/~a/6vFCinlQOiBkf5n-1PqGFkelbSM/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/6vFCinlQOiBkf5n-1PqGFkelbSM/1/da"><img src="http://feedads.g.doubleclick.net/~a/6vFCinlQOiBkf5n-1PqGFkelbSM/1/di" border="0" ismap="true"></img></a></p><p>Windows上Apache+PHP+MySQL的安装配置就不多说了，这篇文章写得不错，全面实用<a href="http://www.leapsoul.cn/?p=695" target="_blank">PHP环境搭建:Windows 7下安装配置PHP+Apache+Mysql环境教程</a></p>
<p>不过我安装好PHP之后，发现Apache启动的时候总是无法加载extention，在log/error.log里面打印一句话：</p>
<pre>PHP Warning:  PHP Startup: Unable to load dynamic library</pre>
<p><span id="more-328"></span><br />
后来把php的安装路径加入到系统环境变量PATH中就解决了这个问题，注意一定是<strong>系统</strong>环境变量，本人最初是傻不啦叽的加入到用户环境变量的PATH里面，结果不起作用。</p>
<p>经过测试PHP的环境搭建好之后，就可以开始配置CakePHP了，我下载的CakePHP解压后放在E:\Working\cakephp里面，下文多出要用到，特此声明。</p>
<p>首先启动Apache的mod_rewrite，在httpd.conf里面找到下面的语句，在118行左右，去掉最前的注释符号(#)</p>
<pre>#LoadModule rewrite_module modules/mod_rewrite.so</pre>
<p>然后在httpd.conf的最后加入以下配置：</p>
<pre>
Alias "/cake" "e:/Working/cakephp"

&lt;Directory "e:/Working/cakephp"&gt;
Options FollowSymLinks
AllowOverride All
Order allow,deny
Allow from all
&lt;/Directory&gt;
</pre>
<p>重启Apache后，访问http://localhost/cake出现”The requested URL /Working/cakephp/app/webroot/index.php was not found on this server.”</p>
<p>这时后请在CakePHP目录下的.htaccess里面添加一行”RewriteBase /cake”，添加之后的文件是：</p>
<pre>
&lt;IfModule mod_rewrite.c&gt;
   RewriteEngine on
   RewriteBase /cake
   RewriteRule    ^$ app/webroot/    [L]
   RewriteRule    (.*) app/webroot/$1 [L]
&lt;/IfModule&gt;
</pre>
<p>然后再访问http://localhost/cake，就可以看到正常的页面的。至于RewriteBase是怎么一回事儿，请参见<a href="http://hi.baidu.com/houdelei250/blog/item/28b69f253ee2663ac8955931.html">Apache Rewrite 详解 RewriteBase</a></p>
<p>最后附上官方的指南<a href="http://book.cakephp.org/cn/view/917/Apache-%E5%92%8C-mod_rewrite">http://book.cakephp.org/cn/view/917/Apache-%E5%92%8C-mod_rewrite</a>，其实这个写得很差。</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/pw0SHUpgB7E" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/03/28/cakephp_win_apache/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/03/28/cakephp_win_apache/</feedburner:origLink></item>
		<item>
		<title>Python从命令行输入中文的编码问题</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/HfZB-hpWF3Y/</link>
		<comments>http://www.zhlwish.com/2011/03/13/reading_chinese_from_cmd_in_python/#comments</comments>
		<pubDate>Sun, 13 Mar 2011 05:52:37 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Python]]></category>
		<category><![CDATA[编码]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=322</guid>
		<description><![CDATA[写了个python脚本自动完成某项工作，需要将从命令行读入的参数写到utf-8编码的文件中，在linux系统中没有问题，因为shell默认为utf-8编码格式，读入后直接写入就行，但是由于Window系统的默认编码为cp936，始终提示编码有错误 <a href="http://www.zhlwish.com/2011/03/13/reading_chinese_from_cmd_in_python/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/FCWy1gYXpSWlBAmbzrkzUOHaVks/0/da"><img src="http://feedads.g.doubleclick.net/~a/FCWy1gYXpSWlBAmbzrkzUOHaVks/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/FCWy1gYXpSWlBAmbzrkzUOHaVks/1/da"><img src="http://feedads.g.doubleclick.net/~a/FCWy1gYXpSWlBAmbzrkzUOHaVks/1/di" border="0" ismap="true"></img></a></p><p>写了个python脚本自动完成某项工作，需要将从命令行读入的参数写到utf-8编码的文件中，在linux系统中没有问题，因为shell默认为utf-8编码格式，读入后直接写入就行，但是由于Window系统的默认编码为cp936，始终提示编码有错误。<br />
<span id="more-322"></span></p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:Verdana,Courier New;"><span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">sys</span>
<span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">codecs</span>
&nbsp;
in_encoding = <span style="color: #dc143c;">sys</span>.<span style="color: black;">stdin</span>.<span style="color: black;">encoding</span>
name = <span style="color: #008000;">raw_input</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;Input your name:&quot;</span><span style="color: black;">&#41;</span>                   <span style="color: #808080; font-style: italic;">#1</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">with</span> <span style="color: #008000;">open</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'1.conf'</span>, <span style="color: #483d8b;">'w'</span><span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">as</span> conf:
    conf.<span style="color: black;">write</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;name=%s&quot;</span> <span style="color: #66cc66;">%</span> name<span style="color: black;">&#41;</span>                        <span style="color: #808080; font-style: italic;">#2</span>
&nbsp;
name = name.<span style="color: black;">decode</span><span style="color: black;">&#40;</span>in_encoding<span style="color: black;">&#41;</span>                        <span style="color: #808080; font-style: italic;">#3</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">with</span> <span style="color: #008000;">open</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'2.conf'</span>, <span style="color: #483d8b;">'w'</span><span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">as</span> conf:
    conf.<span style="color: black;">write</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;name=%s&quot;</span> <span style="color: #66cc66;">%</span> name.<span style="color: black;">encode</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'utf8'</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>    <span style="color: #808080; font-style: italic;">#4</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">with</span> <span style="color: #dc143c;">codecs</span>.<span style="color: #008000;">open</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'3.conf'</span>, <span style="color: #483d8b;">'w'</span>, <span style="color: #483d8b;">'utf8'</span><span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">as</span> conf:
    conf.<span style="color: black;">write</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;name=%s&quot;</span> <span style="color: #66cc66;">%</span> name<span style="color: black;">&#41;</span>                        <span style="color: #808080; font-style: italic;">#5</span></pre></div></div>

<p>解释：</p>
<ol>
<li>为了保证平台无关性，首先使用sys.stdin.encoding取得控制台输入的编码，使用raw_input读入数据</li>
<li>直接使用ANSI编码写入文件，此时生成的文件为ANSI编码格式，中文可以正常显示，但是不符合文件为UTF-8编码的要求</li>
<li>对输入的中文使用控制台的编码进行解码</li>
<li>对解码后的中文字符使用UTF-8编码，此时，输入的文件为UTF-8的格式，满足要求（虽然在open文件的时候没有指定编码，但是生成的文件是UTF-8的编码）</li>
<li>使用codecs模块的open，直接指定输出文件编码，因此不需要decode，可以直接输出UTF-8的字符</li>
</ol>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/HfZB-hpWF3Y" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/03/13/reading_chinese_from_cmd_in_python/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/03/13/reading_chinese_from_cmd_in_python/</feedburner:origLink></item>
		<item>
		<title>Python对象内置函数__str__</title>
		<link>http://feedproxy.google.com/~r/zhlwish/etKj/~3/B6nxlQJk14k/</link>
		<comments>http://www.zhlwish.com/2011/03/08/python_buildin_functions_str/#comments</comments>
		<pubDate>Mon, 07 Mar 2011 17:54:31 +0000</pubDate>
		<dc:creator>周亮</dc:creator>
				<category><![CDATA[Python]]></category>

		<guid isPermaLink="false">http://www.zhlwish.com/?p=311</guid>
		<description><![CDATA[精通Java或者.net的同学在学习Python面向对象的时候总会思考一个问题，Python对象的toString()方法怎么写，怎么样才能print一个对象打印出友好的内容，而不是打印出内存地址？ <a href="http://www.zhlwish.com/2011/03/08/python_buildin_functions_str/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[
<p><a href="http://feedads.g.doubleclick.net/~a/yewdx8nQmH-eGtvaZvWjqqnETfo/0/da"><img src="http://feedads.g.doubleclick.net/~a/yewdx8nQmH-eGtvaZvWjqqnETfo/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/yewdx8nQmH-eGtvaZvWjqqnETfo/1/da"><img src="http://feedads.g.doubleclick.net/~a/yewdx8nQmH-eGtvaZvWjqqnETfo/1/di" border="0" ismap="true"></img></a></p><p>精通Java或者.net的同学在学习Python面向对象的时候总会思考一个问题，Python对象的toString()方法怎么写，怎么样才能print一个对象打印出友好的内容，而不是打印出内存地址？比如定义一个类</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:Verdana,Courier New;"><span style="color: #ff7700;font-weight:bold;">class</span> Friend<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>:
    <span style="color: #ff7700;font-weight:bold;">def</span> <span style="color: #0000cd;">__init__</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span>, name<span style="color: black;">&#41;</span>:
        <span style="color: #008000;">self</span>.<span style="color: black;">name</span> = name
&nbsp;
<span style="color: #ff7700;font-weight:bold;">if</span> __name__ == <span style="color: #483d8b;">'__main__'</span>:
    friend = Friend<span style="color: black;">&#40;</span><span style="color: #483d8b;">'Liang'</span><span style="color: black;">&#41;</span>
    <span style="color: #ff7700;font-weight:bold;">print</span> friend</pre></div></div>

<p>上面这段代码，在我的电脑上输出
<pre><__main__ .Friend instance at 0x7ff3596c></__main__></pre>
<p>我想输出我的朋友的姓名不行么？我想要Java的toString()！<br />
<span id="more-311"></span><br />
其实，可以的，__str__就是toString()，OK，继续完善代码</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:Verdana,Courier New;"><span style="color: #ff7700;font-weight:bold;">class</span> Friend<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>:
    <span style="color: #ff7700;font-weight:bold;">def</span> <span style="color: #0000cd;">__init__</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span>, name<span style="color: black;">&#41;</span>:
        <span style="color: #008000;">self</span>.<span style="color: black;">name</span> = name
&nbsp;
    <span style="color: #ff7700;font-weight:bold;">def</span> <span style="color: #0000cd;">__str__</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>:
        <span style="color: #ff7700;font-weight:bold;">return</span> <span style="color: #483d8b;">&quot;Friend : %s&quot;</span> <span style="color: #66cc66;">%</span> <span style="color: #008000;">self</span>.<span style="color: black;">name</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">if</span> __name__ == <span style="color: #483d8b;">'__main__'</span>:
    friend = Friend<span style="color: black;">&#40;</span><span style="color: #483d8b;">'Liang'</span><span style="color: black;">&#41;</span>
    <span style="color: #ff7700;font-weight:bold;">print</span> friend</pre></div></div>

<p>终于打印出我想看到的了
<pre>Friend name : Liang</pre>
<p>显然的，内置函数带来了这种便利，理所当然要有所约束，那就是这个方法只能返回str，并且只能有self这一个参数，其他的，自行发挥，你懂的</p>
<img src="http://feeds.feedburner.com/~r/zhlwish/etKj/~4/B6nxlQJk14k" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.zhlwish.com/2011/03/08/python_buildin_functions_str/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://www.zhlwish.com/2011/03/08/python_buildin_functions_str/</feedburner:origLink></item>
	</channel>
</rss>

