2009年12月28日星期一

Revised P2PSim-0.3 is ready for download now

The original P2PSim ver 0.3 can not be compiled successfully with g++ 4.3. I have fixed the problem and provided the download of my revision on http://www.fosfer.info. The download link can be found within the “Open download” category. Only  the compiling bug is fixed in this revision, while no any other code is touched. So it’s expected to work as same as the original version. If this download violates any copy right, please let me know.

P2PSim-0.3修正版提供下载

我在http://www.fosfer.info上提供了修正后P2PSim-0.3版本的下载。我只是修正了P2PSim 0.3的版本无法在新的G++ 4.3上无法编译通过的问题。该版本的功能实现上未作任何修改,保持了和原版本的一致。下载在该站的Open download下。http://www.fosfer.info目前还在建站中,今后的发展目标是成为我和朋友们的工作室的主页,能提供各位有用的文档、资料以及代码。

2009年12月27日星期日

P2Psim分析笔记(7)-RPC机制

这是分析笔记的最后一篇,这篇介绍了p2p仿真中最常用的RPC机制在P2Psim中的实现。这篇对P2Psim的仿真机制的最后一部分进行了说明。P2Psim中,不同的P2P协议实现都是基于这个机制来模拟peer间的通讯。
    RPC(Remote Procedure call)的本意是,一台电脑通过网络来来执行另外一台电脑上的函数,函数执行的结果再送回本机。这个机制有很多实现和变形,比如xmlrpc, Soap, 我在这里不扯开了,大家google一下就知道了。因此按照RPC的概念,P2P中peer之间的相互访问都可以看作是RPC操作。因此在P2P的仿真中,仿真软件都不约而同实现一套简化了的rpc接口,这样在应用层的p2p协议只要用这套接口就可以不必理会底层网络通信的细节了。这篇中我给出了RPC实现的说明图。
    图中,不同p2p协议通过调用Node中的doRPC()和asyncRPC()来发送数据给远程的peer。前者是同步的,也就是说,在没收到对方peer的回复或者超时前,本peer就一直死等。后者是非同步的rpc调用。在非同步的方式下,peer调用asyncRPC()函数会立刻得到返回,然后协议得到一个该次请求的句柄,可以理解成取货凭证。然后peer隔一段时间在通过rcvRPC()函数,用这个句柄来查询一下,这个远程调用是不是返回结果了,或者失败了(比如网络丢包)。这好比拿着取货凭证去取货一样。同样如果这个peer收到别人发送来的rpc请求,他也要提供处理相应请求的处理函数。当收到这个请求的时候,相应处理函数被调用。关于请求,我们迟点再分析。我们先逐个分析doRPC()和asyncRPC()的实现。
    当Protocol类的对象调用了Node类中的doRPC()时,Node类首先通过_maktrunk函数把这个请求打包(为了更像一个网络报文?不知道),然后依次调用_doRPC_send()函数在这个报文上面加一个channel(libtask里面的多任务间的数据通信机制)把这个请求的trunk发给Network类的send()接口。Network根据拓扑算出这个报文到达对方peer的延迟,然后生成一个NetEvent事件放入事件队列里。当doRPC()发送了这个数据包后,立刻调用_doRPC_receve()来在这个报文的等待这个数据包上的channel上是否有数据过来,如果有,则从channel中取出这个rpc是否成功的信息再依次返回给doRPC()函数和上层的调用代码。如果成功,这个rpc请求中的返回值指针指向的数据结构已经被对方peer给改写了。以这种方式模拟rpc结果数据的返回。
    当Protocol类的对象调用了Node类中的asyncRPC()接口的时候,机制稍微不同一点。asyncRPC同样调用_maktrunk()封装出一个trunk包,然后让_doRPC_send()函数发送出这个包,但是返回的rpc句柄(取货凭证)被存放到_rpcmap结构中暂时保存起来。然后asnycRPC()函数就立刻返回这个句柄给上层protocol的调用代码了。然后呢,上层代码在之后的事件里面可以时不时通过rcvRPC()接口来查询一下_rpcmap结构里面这个凭条对应的请求有没有得到响应或者是否出错了。
   以上讲完了rpc请求发送的基本逻辑流程,接下来说一下rpc请求被接收的流程。上篇我说了,当EventQueue处理NetEvent事件的时候调用其execute()会导致Node中的Packet_handler()接口被调用。这个接口函数会区分,该消息对应的是rpc请求还是rpc应答。如果是应答的话,他就这个报文通过其channel(记得在_doRPC_send()中建立的channel么?)发送过去。 如果_doRPC_receive()正在等待channel上的数据,这个数据就会让_doRPC_receive()返回,完成同步RPC。如果这是一个异步的rpc,无所谓,这个数据就存在channel里面了,等peer调用rcvRPC()去查询和收取。
  如果这是一个请求事件,那Packet_handler()就建立一个新task来运行receive()函数。这个函数中,这个事件中rpc的请求类型会被拿出来分析,对应不同的事件类型,protocol里面的不同事件处理函数会被调用。也就是说Protocol对象实例中的相应RPC处理函数“被”执行了。根据执行结果,receive()函数构造出RPC响应数据包,然后再通过Network类的send()结构最终又变成NetEvent事件插入到事件队列EventQueue里面去了。至于RPC的响应如何处理,上一段已经说过了。

无命名

P2Psim分析笔记(6)- 仿真中的事件机制

    这几天由于P2Psim的分析进度不是很快,所以一直也就没有更新分析笔记,希望大家见谅。在前几篇中,我已经大体介绍了P2Psim的初始化过程。对初始化的分析,到上篇就告一段落。由于我是一边分析一边写笔记,所以有些细节方面可能存在遗漏和错误。如果各位在自己的分析中发现,不妨联系我。在每篇笔记的图片中,有我的邮件地址的水印。

    接着之前的分析,本篇主要介绍了P2Psim的运行机制。这部分的理解,是以后用P2Psim来添加自己的p2p协议的基础。这篇的介绍不涉及太多细节,因为在我的分析中,发现Node类的实现中有太多的细节需要说。所以在这里我只是给大家一个总体的介绍。如果大家去做代码分析,我建议大家分析sillyprotocol,而不要一上手就去看Chord协议。我个人的感觉是,Chord协议涉及太多协议本身的机制,它的机制本身的复杂性,很大程度上会干扰大家对仿真中的消息机制的分析。而sillyprotocol几乎没有什么代码和任何协议机制。因此是一个很好的切入点。

   按照惯例,我给出了分析的简单图例。由于这图是用office的onenote画的,虽然画起来很方便,但是onenote的画图功能实在太弱了,所以不同意义的先只能用颜色区别,而无法用线形来区别,大家只能凑合着看了。

   图中左上角的EventQueue是我介绍的切入点。在之前,我介绍过,他的运行机制就是在不停的调用他的advance()函数从消息队列里面取出事件,然后每次取出消息就去kick一下消息发生器类EventGenerator,然后再对取出的每个event对象,调用其execute()函数来完成相应的操作。那么EventQueue中消息的来源主要是两个: EventGenerator类或其子类;和Node类。

   先看EventGenerator类。这个类在把自己注册到EventQueue实例里面的时候就把仿真结束消息(exit)和各个peer加入仿真的消息(join)加入了队列。前者是SimEvent类型的消息,后者是P2PEvent消息。SimEvent类型的消息只有一个用途,就是结束仿真。P2PEvent事件的用途就是通知各个peer在不同的时候做不同的事情,比如join,crash和lookup这些。不同于其他的仿真软件,如OverSim,P2Psim中P2PEvent事件是由EventGenerator做中心控制的,而不是由各个peer自己控制的。换而言之,EventGenrator控制了全体peer的行为模式。这点简化对于homegeneous的仿真而言是好的,写代码就容易多了。如果要做geterougenous的仿真就困难一点了,不过也不是大问题。

   第二个事件的发生源是Node类。Node类封装peer作为网络结点的角色。对上层p2p协议,Node提供了RPC调用接口。然后把对应的RPC请求和应答转换成网络报文的传输。在仿真中,报文的发送和接受都被转换成NetEvent网络事件。当Node要发网络数据包的时候,他就从Topology对象提供的接口计算出报文到达的延时,然后生成一个报文到达的NetSim事件,放到EventQueue里面,等待EventQueue到时候进行处理。

   介绍完事件的发生源,再说说事件的处理。之前说过,EventQueue在取出Event时候,会调用其execut函数来处理事件。对于不同类型的事件,其execute机制不同。 最简单的是SimEvent的,立刻就通知系统结束仿真了,具体代码各位自己去看。其次是P2PEvent。如果消息对于的操作是EventGenerator让peer join或者crash,他只是把protocol中对应的_alive进行置位和清位。如果是其他操作,如chord中的lookup,这类。他会对应找到protocol对象中的函数调用来完成处理。比如lookup事件, P2PEvent 就把Event中对应的node对象找出来,调用他的lookup()函数.

   如果处理的是NetEvent事件,它的execute会根据事件的类型进行区别对待。之前我提到,Node会把RPC操作转变为网络报文传输,因此NetEvent对应不同网络报文也分两类:请求和应答。如果这个事件对应的是请求,它就让系统为对应的接收结点生成一个新task来跑Node::receive()函数,让node来接收这个“网络数据包”。否则,他就把这个数据包发送到对应的channel去,让等待接收RPC回应的node的()来接收这个回应。

无命名

2009年12月23日星期三

P2Psim分析笔记(5)-EventGenerator and Observer

    本篇笔记,主要是跟踪taskmain()函数中EventGenerateor::parse(event_file)。本篇主要涉及EventGenerator的构造流程,其中对churnEventGenerator类和ChornObserver类进行分析。下面的图示给出了EventGenerateor::parse()函数的调用流程。

    图中EventGenerateor::parse()的调用很简单,首先读取eventfile 里面关于eventgenerator和observer的名字。生成了一个generator实例,然后通过thread()把对应的eventgenerator的任务个激活。最后再生成observer实例。这里我分析了ChurnEventGenerator 和ChurnObserver两个类。按照我的理解Generator主要用于生成对应protocol的node的初始化事件,比如node什么时候开始活过来,以及对eventqueue类实例化和进行激活等操作。observer 的设计本意是用来统计和记录仿真中的各个事件。在P2Psim的设计中,observer的实例化中,observer把自己注册到各个node对象中,这样每次node发消息的时候,在消息队列处理消息的时候,都会把这个消息上的observer拿出来,调用一下他们的kick()来修改observer中的统计信息。

   图中,首先EventGenerator::parse()调用工厂模式生成了eventgenerator实例。我们以churnEventGenerator为例。churnEventGenerator在构造对象的时候,首先读取了所需的参数。图中列出了所有参数,这些参数的具体用途以后再分析(目前我也不清楚,呵呵)。然后实例化了消息队列,并把自己注册为消息队列的observer,这是一个特殊的observer(具体的用途目前也不清楚,估计是每次消息队列处理消息的时候,都能被调用一次)。

  在消息队列的实例化中,消息队列eventqueue,建立了一个特别的channel,然后就调用自己的thread()触发了run()函数变成一个并发任务。run函数首先会在这个channel上等待一个go消息(这个消息会由eventGenerator的实例触发,见图中黄绿色箭头),当收到这个go消息,run()就循环调用advance()函数来处理消息队列里面的每个消息。在处理每个消息的时候,每个消息上的observer会被kick()一下,然后消息队列会执行event上的execute()函数来处理这个消息对应的事务。

      在EventGenerator::parse()生成eventgenerator后,第二件事情是调用了这个实例(churnEventGenerator为例)的thread函数,然后这个消息发生器对象就开始作为一个并发任务开始运行其run()函数了。在其run()函数中,我们可以看到generator的主要工作了:首先生成了一个仿真结束消息,然后从network实例中要来了所有的node信息,把他们都维护在本地的数据结构里面,并把wellknown结点告诉他们,这样他们一开始就能知道他们到那里去找access point。然后设置每个node加入p2p网络的事件。当然,wellknown结点是最早加入的(不然别人找不到他了)。最后给eventqueue发一个go消息,eventqueue就开始处理消息了,整个仿真就开始了(但是由于没有调用yield(),当前任务还没进行切换,所以在物理上那些任务一个都跑不起来)。

    再回到EventGenerator::parse(event_file)函数,最后一步是通过工厂模式建立了observer对象实例。以churnObserver为例,他的工作也很简单,从Network对象实例里面得到所有的node信息,把自己的指针加入他们,这样他们发送消息在消息队列处理时observer就会被触发了。

总结: eventGenerator 是注册在eventQueue上的observer,而普通observer是注册在node上的。

无命名

2009年12月22日星期二

P2Psim分析笔记(4)-Topology 和Network

  在上篇的分析理,taskmain的第三步是让Topology类来分析topology_file,从而启动了Network对象。这次,我主要介绍这部分的详细流程。主要内容包括对Topology类以及子类Euclidian拓扑类的机制分析,Failure Model类以及Network类的交互。搞清楚这些,基本就把P2PSim的启动机制搞清楚了。按照惯例,我在这里给出了所涉及的流程的大体流程图。
无命名
   
    这部分的调用是taskmain函数中的Topology::parse(topology_file)引起的。在pase函数中,首先从topology_file里面读出了topology的名字,例如Euclidian拓扑, 以及对应的failure模型。至于failure模型,好像是用来制定数据传输中的丢包策略的。这个目前不是我的兴趣所在,所以我也懒得去仔细分析了。如果在topology_file里面不指定的话,在这里会默认提供一个无丢包的nullfailure模型。
   在生成topology和failure模型中,他们的构造函数都不会做什么特别的工作。然后这两个对象top和fm被作为参数来构造Network的对象实例。在Network对象的构造中,topology和failure模型会被保存到Network对象里面。以后只能有Network的实例来访问了。最后Network对象构造中会调用thread来让run函数作为一个task来跑。这个函数中,Network实例开了一个channel(libtask中task进行通信的机制),然后就不断从这个channel读取来自topology对象的Node(也就是peer)信息。然后存到自己的_nodes成员中,这个成员是IPaddress 和Node指针的一个map。
  最后,Topology::parse()调用了topology对象的parse完成了topology_file的剩余部分的解析。这里要注意toplogy对象(top指针 )是指向Topology类的一个子类的对象,比如Euclidian类的对象。 接下来,我们拿Euclidian拓扑来举例,这个对象按照
        IPaddress  x,y
的格式来解析peer在空间中的位置,以及用ipaddress来标识peer。解析出每条记录,都通过工厂模式,构造出一个Node类的子类的对象,除了保存在自己的_nodes成员中(也是一个IPaddress 到node的map),通过channel发送给Network对象的run函数。图中的黄绿色箭头表示出这个联系。

2009年12月20日星期日

P2Psim分析笔记(3)-taskmain函数流程

    在上篇里,我们知道P2PSim是基于libtask的,libtask的第一个任务是通过taskmain函数来启动的。换而言之,taskmain是p2psim的主程序。下面的图里面给出了taskmain的主要流程。



    根据图示,taskmain先把-开头的参数解析出来,然后让Node类去解析protocol_file,然后让Topology类去负责解析topology_file。Topology在解析topology_file后调用Network类生出了第一个并发任务,这个任务负责根据topology建立peer的vector。随后调用了yield放弃cup让Network任务去充分处理topology对应的Peer生成工作。
    然后,taskmain让EventGenerator类根据event_file生成了对应的事件发生器(EventGenerator)的对象,这里采用了工厂模式,根据配置文件生成对应的事件发生器。同时还生成对应的观察者对象。 生成的发生器对象也是一个从Threaded派生的家伙,因此此刻第三个并发任务也开始运行了。
    最后,taskmain遍历了所有的node对象,让他们完成初始化。随后完成所有工作退出。

2009年12月19日星期六

P2Psim分析笔记(2)-程序架构简述


这是我整理P2PSim这个仿真软件包的第二篇笔记。第一篇是P2PSim在g++ 4.3下的编译,在第一篇里面介绍了P2PSim 0.3在编译和按照中的碰到的问题以及解决方式。本篇主要给出P2PSim的实现架构,帮助需要进行代码分析的朋友对P2PSim能有个大体的构架了解。在些这篇时候,作者也还未完成对整体代码的通读,所以对全局的掌握还不充分,如有错误,请各位指出和包涵。



P2PSim简述
    这是一个比较简单的p2p模拟软件包,是MIT的一个老兄搞的玩也。在2006年出了最后一版0.3后再没更新了。需要的朋友可去http://pdos.csail.mit.edu/p2psim/下载。国内不少paper用这个软件包来做仿真,网上也有不少的代码分析笔记,比较详细的是kikiKind在CSDN上的p2psim学习笔记,但是写到后来就晦涩难懂了,完全不是给旁人看的。他给出了p2psim中类的继承关系图,以及关于vividi这个错误的fix。那个类图的资料在P2Psim的官网上很难找到链接了,所以这是kikikind朋友的最大贡献。但是他给出的贴图却是错误的,把第一张图贴了两遍,第二张图给漏了。然后所有网络转载都一样错。此外我在g++ 4.3上碰到更多的错误,他都没有提及,因此不是很全面,此外他在对libtask以及main函数的分析都很粗略,让人很难跟。综合来说,这个笔记是他写给他自己看的,而不是给网友看的。我个人不是很满意,所以我在这把他所遗漏和错误的地方都补上。希望对各位有用。在本篇笔记里面,我从便于各位读者理解学校的顺序来组织内容,而不是从代码分析的学习次序来说明。


    首先是P2Psim的实现基础。这个软件包的实现是基于单进程多任务方式工作的。他本质上是基于一个叫LibTask的C语言软件包来实现在单个进程内进行多个任务的调度和切换。这个包在他的源代码的/libtask目录下。 这个包是MIT开发的,目前在google code的网站上有登记,地址是http://code.google.com/p/libtask/,可以在这个网站上查到这个库的基本api的说明。可以直接看这个说明来理解这个库的实用,而不需要去看/libtask目录下的代码来分析到底这个库在做什么。此外,在P2PSim里面,作者把这个库封装到了Threadmanager和Thread两个类。前者Threadmanager用来封装全局的task的pool的,而后者封装了各个task的api。这样P2PSim就实现了C++这级的多任务调度。
    其次,我把kikikind老兄的类继承图重新贴一遍,来帮助大家理解程序架构。在这个图里面,我们看到从threaded类一共派生出EventQueue, Network,和EventGenerator三个类,这三个类就是程序在运行时候的3个主要并发任务。















至于图中的其他部分,等以后的具体分析的时候再慢慢说明。
    因此,综上所述,P2Psim是一个根据libtask所提出的架构所写的一个程序,因此在/p2psim目录下,main.c程序里面没有main函数,而是taskmain函数,这个函数会被libtask作为第一个task而调用启动,功能类似main函数,连调用参数都差不多。然后在这个taskmain中,间接建立了上述其他几个并发任务。
    到这里,读者应该对p2psim的大体构架有个简单认识了。 下次我打算把taskmain函数里面的初始化顺序介绍一下。

2009年12月18日星期五

我的小服务器

朋友做了一个工控机的板子,我要了一块来,自己加上了迅驰1.2G CPU,再从笔记本上拆了一个1G内存和老的移动硬盘 30G IDE,就算搭起了一个最简陋的服务器。此外我从破DVD光驱上拆了一块铁皮底板,打了几个洞,把主板和硬盘固定起来,现在可以不用在桌子上“摆地摊”了。打算用这个服务器做个人web server。在朋友那里测试的结果,板子加硬盘的功耗只有30W,相当低功耗了。符合绿色环保理念。


2009年12月17日星期四

一位亿万富翁的素食原则(zt)

一位亿万富翁的素食原则


旺度居士


全球500强之一的AT&T公司亚太地区前总裁温先生今天视察了我们公司。他现在是一个拥有数亿资产的香港出版公司董事长,一位慈眉善目的中年人。

中午由我做东,请他吃饭。亿万富翁要吃什麽呢?我有些茫然。珠海虽然颇多山珍海味,但要让温董吃得满意,究竟需要怎样的排场?

谁料温董轻言轻语∶“方便的话,我就吃素!”於是,我们顺便进了怡景湾大酒店旁的西餐厅。

温董、刘先生、我及LD一行四人,点了四份商务套餐。我们的三份,有荤有素;温董的那份,还真是全素。

席间,我向温董请教吃素的益处。温董的一番素食理论,听得我心服口服┅┅

(温董的话)

简单原则

一谈到吃素,就会被许多人问及“修行”的事,总是被弄得很茫然,不知道应该回答什麽,每每想起前一段时间的一次对话,只涉及到一些简单原则,比谈“修行”容易多了。起因是去日本交流,这天中午他们知道我是素食者。

“你什麽都不吃吗?”(每个人都忙著劝别人吃,有人客气的问。)

“我刚才吃了一个苹果。”(我礼貌的回答。)

“他是一位素食者。”我的同事放了个炸弹。客气的寒暄显然不如这个话题有趣,大家如同看斑马一样一起盯著我。

“你信仰什麽宗教吗?”(为什麽每次都要问同样的问题。)

“没那麽复杂,只是生活方式略有不同。我的原则很简单,尽量不伤害别人。”

“可动物不是人!”

“我们喝著牛奶长大,它辛苦种地让我们吃,当它哭著求你不要杀它和它的小孩,你是否下得了手?你是否忍心?小时候大家都玩过老鹰捉小鸡的游戏,那表示它们的母亲不希望它的小孩受到伤害。它们打不过你。但你不会利用你的强大去欺负别人吧,”

“那你肯定反对我们吃肉。”

“我不会把刀架在你脖子上的,这也是一个简单的原则,如果你喜欢吃苹果我逼著你吃梨,那也是暴力。你快乐著你的快乐,我幸福著我的幸福,於是天下太平。只是你要了解自己在做什麽,结果是什麽,并且肯承担,那你有权选择你想要的生活,不一定要和我一样嘛。”

“可是你不伤害别人,别人也会伤害你。”

“你总不能因为别人偷了你的自行车你就去偷别人的自行车吧。”

“养那麽多鸡不就是给人吃的麽。”

“好像在南北战争时期就有人说∶黑人天生就是奴隶,他们的儿子、儿子的儿子天生就是奴隶。”

“我很佩服你,面对这麽多美食能忍得住。”

“我不会虐待自己的。他们对我没有吸引力,我不需要忍的啦。我刚才已经吃了一个苹果,香甜而且多汁,(席间已经有人为我点了一盒牛奶),瞧,我还有牛奶,并且每个人都很关心我是否够吃,够营养,小小的善意就得到了很多回报,这世界真的很公平的。”

“你真的适合信一个什麽教。”

“这跟宗教没有关系,只是一些简单的原则,我不会啃著鸡腿给我的儿子讲动物是我们的朋友,这样做的结果是他不仅没有学会仁慈反而学会撒谎,因为你心口不一。有很多事情是我们在幼儿园里就学过的,比如说∶大家都是好朋友、撒谎不是好孩子、自己的事情自己做、有礼貌、帮助别人、好好学习、天天努力向上、讲卫生、爱劳┅┅,这些都是极其简单的原则,就是要认真地去做。总不能长大了还不如一个小孩。”┅┅┅┅

时间久了,很多对话记不住了,不外乎把这些简单原则应用到生活和工作上,但是这些被重新提及的简单原则已经跨越午餐成为延续到下午的话题,也许还会延续到他们的生活中。许多人连小孩会的事都不会做,小孩懂的事都不懂,却谈论著这个经典那个法门,不知道爱的人满嘴都是感动,自私的人却在谈著奉献。我真的不知道什麽是“修行”,那麽复杂的事还是交给那些“大修行的人”吧,让我简单的活著,多做事少说话,这也是一个简单的原则。

我为什麽成了素食者

当您真正了解肉类是污秽不洁的,又具传染病的尸首时,您能再面无惧色的狼吞虎咽吗?

在我逐渐弃肉而吃素的过程中,我没作过任何所谓的"牺牲",所有食物没勉强放弃过一样。我虽相信,人在生活中善自保重身体,是信仰的一部份,但我个人在弃绝肉食中,与信仰毫无关联。

我不吃任何肉食和任何维他命丸,也健康的活了半辈子。我在美国旅行多次,常在饭馆和别人家中吃饭,桌上虽也有肉类,但丝毫不曾影响我的饮食与情绪。弃肉吃素的经过,未曾使我作难,也没有勉强的感觉。让我慢慢道来吧猪肝的脓包里竟有一窝煮熟的小虫,牛的一整叶肺给结核菌蚀烂了;动物的病菌会寄生在人体上。

....在旅行时,有一天吃肝咬了两三口,觉得味道不对劲,再用刀子一切,真把我吓了一跳,脓包里竟有一窝小虫,早己煮熟了。从那天起,每逢看见肝我就反胃。

....我本来最爱吃碎牛排,就是用绞肉机绞碎的。听别人说,商人常搀杂各种劣等的零碎物,所以每次我都亲自挑选一块漂亮的牛肉,叫他当面绞碎。我觉得这样作很精明。

....有一天,我发现自己并不精明。因为排在前面的一位老兄,等著绞他的猪肉。同一个绞肉机,既不消毒,也不洗,它内部的构造我更清楚。这时我才领悟到前面的人留下半磅猪肉给我,而我的半磅混合肉要留给后面的那位顾客。从此,碎牛排再也不能逗引我的胃口了。

....我虽不再吃碎牛排,但是牛肉仍是我所喜爱的,直到一件事震撼了我,我才全然断绝牛肉!!

....事情是这样的,我的邻居从牛群中挑了一只最棒的母牛,供应他自己的牛奶。某天,卫生员来检验,说只牛有结核病,应予销毁。邻居说他不相信,置之不理,后来,另外的检验员又来检查,报告的情况相同。

....我的邻居仍不肯相信,他勉强的把牛送往一个较大的屠场,获得许可,观看切割。出现在他眼前的,是一整叶被结核菌蚀烂了的肺!

....回到家里,他极为烦恼。他得的那笔代价还不错,比同量的肥料价钱贵多了。但是,他一直在想,那只牛身上的其他部分,是不是健康无病菌呢?是不是可以食用?

此事过后不久,我领著班上的学生去远足,路过该屠房,大家看著各种动物的尸体,在吊车和输送带上运送著。我就问那位作向导的政府验肉员∶『请问老兄,如果一头牛害结核病,一叶肺烂坏了,您们怎样处理呢?』

....『我也请问你,你的苹果上有个烂斑,你怎麽办?你还不是把它削掉,然后吃下去吗?我们也是一样作。』....我注意到学生们脸上吃惊的表情。上次我曾向他们讲过那只病牛的故事。等出了屠场,我问他们削苹果和割牛肉是否相同。

....『不同,开玩笑!』异口同声的否定著。他们说∶『病肺的血液会周流全身。』於是我又向他们指出另外的不同点∶动物的病菌会寄生在我们的人身上,而苹果的酶菌只会活在果菜上面,再者,它也不会周流回圈。就算把苹果的烂疤吃下去,也不致于害病。

....这样一来,过去使我讨厌的某些肉食,越发使我讨厌了。

鸡场里,那些垂头丧气、屁股潮湿的劣等鸡都进了市场,加★工场。

....过去我爱吃鸡。但参观附近的一个养鸡场之后,这方面的食欲也没有了。我看到,养鸡人天天巡视鸡房,把病鸡和少下蛋的鸡挑出来,送去市场。那些垂头丧气、屁股潮湿的家夥,都进了加工厂。使我吃惊的是,至少在那时候,根本就没有任何检验工作。胃好像告诉我,别再把死鸡送进我的皮袋里去了!

★某些山涧里,有百分之九十的鱼的染患癌症。

┅┅鱼,我还是吃,有时还开玩笑的说∶「鱼一定是乾净的,它们起码每天洗一次澡呢!」....某次,同朋友去亚利桑那州某山涧钓鱼,我搞不清到底是甚麽毛病,但我知道所钓到的鱼中,将近二分之一是有肿瘤的,或在内部,或在外部,看了令人倒胃口。查阅有关资料,我才从政府报告得知,有些山涧里,鱼癌流行,尤其是鳟鱼。其染病率有的高达十分之九。

★那些小鱼

┅┅还有,一些装罐的小鱼,如沙丁鱼等,根本就没有清洗过,连五脏,带粪便,一股脑儿的装进铁盒里去.................

请珍爱生命

看见报上的一幅图画,一口烧热的油锅中弓身著一条鳝鱼。图画的插图大意是说,下油锅的鳝鱼极力弓起身体,厨师不解,拿出鳝鱼用刀剖之,才知其腹内怀有一条小鳝鱼,它是为了保护腹中的小生命,努力的弓起了腹部。

听友人讲起一件他目睹的很悲惨的事。一条有黑缎般光亮皮毛的雄性狗,离开刚下狗娃的花狗准备到街对面不远处的一家肉食小店去拾一些骨头。大约是被爱情及爱情的结晶冲昏了头脑,它从北向南穿过十字路口时,没注意到一辆微型客车正从东风驰电掣般开来,“21712;”的一声,被车撞了个正著。车子几乎连速度都未减一下,就开跑了。车子刚刚离开,狗就在车子喷出的废烟中,一个鹞子翻身站起来,撒腿往肉食店跑去。在它被撞倒的路中间,有滩红色的血慢慢向四周流动和凝固,象一个心的形状。血中间漂浮著几根黑亮的毛。

黑狗迅速地跑到小铺子,用嘴拾起一根粗大的带肉的骨头,转身又飞一样奔回它的花狗和小狗娃的身旁,并将拾来的食物喂给了它们。这一系列行为在不过10分钟内全部完成,而且,当它把捡到的骨头转给花狗时它就无力的垂死般地倒在了花狗的身旁。谁也不会想到,从路上站起来跑掉时,“身手敏捷”的黑狗怎麽会在一瞬间死去。

友人说,黑狗将骨头转给花狗时,它听清了它们相互间那种类似安慰的,狺狺的低语。与它们的声音不同,它们的眼睛都充满了那麽深深的哀痛,悲伤。尤其是黑狗的眼睛,似乎是含著泪光,充满对生命的留恋,它那麽固执地看著自己的爱侣,看著自己的孩子,连眼睛都不转一下。那种目光,即使铁石心肠的人看了都会心颤。

我还知道,几年前冰岛政府否决了原本拟定的再次允许捕鲸的计划,原因是“找不到能使鲸迅速了结痛苦的捕鲸枪”。

在引起我们兴趣的事件日益增多的日益刺激的今天,珍爱生命这件事显得书生意气。然而,假如阅读黑狗含泪的眼睛,鳝鱼竭力弓起的身体,以及听到冰岛政府人道的尊重生命的决定,心不猛烈的跳动,并向生命致以你最诚恳的敬礼,那麽,活著就失去了它最本质的快乐。不是吗?

我在这样一个阴郁的漫长午后,开著起亚嘉华行驶在珠海的情侣路上,一遍一遍的回想温董的话和这三个与生命相关的片断,它们就象挂在屋檐下风乾的萝卜条,让你记忆生命曾经是那麽饱满,丰润和微光闪烁。而珍爱生命,就象用泉水去浸泡萝卜干,无论是哪一种形式的浸泡,都会让人看见生命恢复原状的过程,一种世间最耐人寻味的过程,一粒种子到开放花朵的过程。

听了温董的一席话,我暗下决心,一定要成为一个素食者。

P2PSim在g++ 4.3下的编译

因为科研需要,需要找一个高效的p2p模拟器,能称得上高效的,并且支持简单拓扑的,也就p2psim了。但是p2psim在2005年已经停止更新了,而且没有多少文档,因此要自己摸索有些问题。
在安装中,我用的是Debian 5.03 lenny平台。g++是4.3版本。下载到的p2psim 0.3版本无法在g++4的版本上进行编译通过。网上最简单的做法是用老版本的linux。这是我不屑做的事情。经过一个下午的折腾,终于把所有编译问题都解决了,在这里做一个问题解决的总结。以便后来人。
我碰到的问题一共有6类。按照出现和解决的次序分别为:
1:hash_map STL错误, C++库更新造成的问题
2: strcmp未申明, g++对缺省include变严格了
3:类函数 Node:xxxx: C++语法版本
4:代码错误 vividi:  作者的低级错误
6:bighashmap.cc include问题: 还是觉得是C++语言机制问题
5:STL里的assert错误: 不清楚原因

1. hash_map STL错误
这个问题g++会提示用到了ext/hashmap这个文件,这个文件已经过时了,现在建议用unordered_hash.解决办法,在configure里面找到DEF定义,加入-Wobsolete 来抑制这个警告就可以了。然后重新configure 和make。

2: strcmp未申明
这个问题很容易解决,在公共包含的.h文件里面引入#include 就可以了。还是新版本的g++变严格了的问题。

3:类函数 Node:xxxx:
在很多.c文件里面,出现了static的类函数前面加上类名字。比如Node 类里面的abc函数是Node::abc(),我不知道这是那门子C++方言。反正在4的版本中g++不允许了。把这些类名去掉就好了。

4:代码错误 vividi
在vividtest.c里面vividitest类里面,有个半吊子成员量定义,用的类型是vividi,从来没被用过,看来是作者的低级错误。注释掉就好了。


6:bighashmap.cc include问题:
这个问题很混蛋,在ld做连接的时候,出现HashMap<>:xxxx()找不到的错误。HashMap是在bighashmap.cc里面声明的,被include在node.c里面了,但是其他地方都没有include. 作者的原意是把模板当作普通类,希望在node.o里面包括,然后连接到其他的.o里面去。真是疯了:C++的模板是源代码级别的展开,根本不可能这么搞的。我改成在所有公共的.h头文件里面包括这个cc文件。


5:STL里的assert错误:
在bighasmap.cc里面 HashMap类模板里面用了不少assert来做出错检查,但是g++觉得这是不允许的,所以统统注释掉就好了。然后就编译通过了。

总结g++ 3.x是个跑单帮的,啥方言都懂,现在到了4.x版本,完成原始积累,开始打高尔夫,说官话。

2009年10月13日星期二

Back track 和slax

前几天用了一下bt3,就是有名的蹭网卡随带的破解软件。发现这个东东是基于Slax Linux发行版。查了一下Slax的网站,发现他的主要特色是可随时携带。就是我一直所希望的。这几天打算仔细研究一下。

2009年9月18日星期五

青蛙王子的魔咒

记得从有了QQ开始,我一直用的是青蛙头像。最近突然发现这是个魔咒。历数我所偶遇的程序bug,真的是太多了。神奇的是我往往会在学某个软件的第一时间碰到bug。难道我真的是青蛙王子?最近我用scilab,结果不到两天就发现了scilab 的画图输出成矢量图的时候有bug. 然后我用octave, 按照tutorial尝试的第一条命令是 clear all,结果octave立刻crash了。看来我还真是注定吃苍蝇的角色啊。真是郁闷。

WINTEL的阳谋

为什么每年我们都不得不花钱更新我们的计算机硬件?但又为什么已经付了这么多钱,我们还总觉得我们的计算机越来越慢?最近,我开始想明白这个道理了。从经济学的角度,我们实际是中了微软和Intel的阳谋。
看一下现状,微软带领的window阵营一直引领着软件开发质量和性能越来越差,而软件体积越来越庞大的的趋势。从Windows操作系统平台,到Office 系统, 软件的体积都在以成倍的速度增长。到目前,我们的系统安装已经无法用CD介质来满足。新出的Vista和我们当前在使用的Office 2003或者2007,都不得不使用DVD光盘来安装。或者在我们所买的品牌机上,需要永久占据5G到10G的硬盘空间。
但是,我们所得到的软件质量是不是更高了?不是的,随着软件体积的庞大,以及微软为了更快的引入新的功能保持对软件业的领导地位,软件质量和性能远远不如以前。原来只需要几十兆的软件系统,现状以及增长到几个G的大小。然而这并不是因为带来了相同数量级增长的新的功能,而是为了加快开发进度抢占市场而忽视了性能和稳定性。包括微软在内,大多数的软件现状都是补丁盖补丁。如果你买一个软件,一年以内不打个3个补丁的情况是不可能的。看一下ActiveX和Dcom的设计,整体构架都低效率和不稳定。以一个日常的例子而言,如果用Word打开一个文档出现错误,所有打开文档的独立Word窗口都会崩溃。为什么? 因为所有的word都基于同一个DCOM组件。再一个例子就是DirectShow视频播放框架。无论在开发中如何小心翼翼,都没法避免最终程序的莫名其妙崩溃。原因也是一样,用组件搭成的软件,就好像用积木搭成的皇宫一样,随便抽掉一块就会倒。而这些组件的质量因为要求快速开发而大多低劣。即便是微软自己开发的组件,都无法保证在自己的操作系统上可靠运行。
那么当下这种情况的获益人是谁? 微软和Intel。 软件做的越大运行越慢,就需要更高的硬件配置来运行,Intel就财源不断。软件只求开发速度不求性能和质量,又帮助微软遥遥领先其他对手,必死对手。此外质量的低劣又为微软卖完win32卖98,买了98卖2000,卖了2000卖xp提高了源源不断的财源。每次升级,付出的至少是50%的支出(软件升级安装),或者100%以上的支出(购买新版本软件)。那么从98到vista,我们的确获得了5.06倍(以升级安装50%的额外支出为例)或者16倍(以全新安装为例)的功能和性能的提升?肯定没有,而且我们还得在硬件投资上加倍投资。
我所说的这些,并不是说技术的发展不重要。人类的确需要更高的科技来提升生活质量和环境质量。比如减少计算机的功耗,提高计算性能,降低计算机的寿命和报废后的环境影响,这些都是需要科技的进步。 但是更应该提高软件的性能和质量。WinTel的这种把戏,只是在以科技进步为借口,在讹诈计算机的消费者,实质是制造一个消费的巨大黑洞。

2009年7月9日星期四

JabRef: BibTex数据库整理软件

写论文最让人头痛的事情之一就是整理参考文献。原来写paper用的是word,参考文献搞来搞去每次都让我恨的牙痒痒。后来发现学校买了EndNote,试用了一下,觉得一般般,而且和我喜欢的word2003还多少有些不兼容。重装了几次系统之后就把这个又贵又naive的玩也扔到脑后了。后来发现Letax是个好东西,写paper都不用考虑格式排版。之后又接触了BibTex. 这个东西做参考文献太强悍了。所有的科研出版数据库都支持输出BibTex格式的参考文献信息。写paper的时候直接包进来就可以了。 然后碰到最好一个问题。 文章文献多了,不好管理。而且有些古老的和冷门的文献没有现成的BibTex可以用,就得自己做。 JabRef就是我需要的最好工具.它提过了bibTex强大的管理功能。 条目归档修改和在多个bib文件之间复制粘贴都只要动动鼠标就可以了。 虽然刚开始我顾虑它是Java写的,可能很懒。但是事实上根本感觉不出他在界面,操作上的差异。真是一个免费又好用的东西。

环保,绿色,高效的firefox插件:adblock plus

今天偶然在网上看到一篇文章,关于如何过滤gmail中的广告,引起了我的兴趣。根据文章我用了用firefox的插件 adblock plus。这个插件安装和设置很简单,只要在firefox的工具->附加组组件中找到它安装就可以了,安装后选择了它网上的几个主要的过滤列表。这下打开hotmail和gmail。发现旁边的几个广告都消失了,而且由于不需要下载广告图片,浏览器打开网页的速度也明显快了。此外,可以根据自己的需要,把浏览中碰到的广告自定义屏蔽。这个世界一下子就安静了。

2009年7月7日星期二

TeXnicCenter 使用笔记

简介
TeXnicCenter是Windows下最好的开源免费Latex IDE。但是从2008年底推出1.0stable版本后就一直停滞不再推新版本

笔记
(1)使用IEEEtran模板中关于bibTex的问题
在TeXnicCenter中在使用Michael Shell提供的IEEEtran模板撰写IEEE会议文章的时候,会出现bibTex错误。

错误重现:
所用的TeXnicCenter版本是1.0_r1 stable,新建一个空project后,在主tex文件里面复制会议模板bare_conf.tex内容,能够正确编译生成pdf. 但是如果把参考文献部分改成:
\bibliographystyle{IEEEtran}

\bibliography{paper}
则编译出错且无法生成PDF文件。查看编译输出,原因为IEEEtran.bst会生成一个不含任何item的参考文献列表脚本(.bbl文件). 使得Latex编译出现语法错误。如果在bib数据库文件里面加入参考,则IEEEtran.bst仍然拒绝生成,理由是tex对于的aux文件里面没有\cite{}命令,所以他认为它不必编译生成参考文献条目。此后即便在tex里面加了\cite{}引用,仍然同样出错。出错在于TeXnicCenter的编译顺序安排有问题(因为lyx就没任何错误)。

解决步骤:
1. 先加入.bib文件的内容;
2. 在.tex文件里面加入对应的\cite{}
3. 对.tex文件进行编译,不怕出错,只要生成.aux文件就可以
4. 对.bib文件单独run一次BibTex, 这次BibTex不出错了
5. 对.tex进行build, build 通过,完成。

后继的一些错误及其解决:
此后如果对.bib有修改和在.tex里面修改和添加\cite{},build的时候经常出现error 和 warning。也是同样的原因,但是多build几次,这些提示就会消失(一般为3次)。不会再和一开始的时候那样顽固了。

(2)不能使用独立子目录的问题
TeXnicCenter的编译不支持子目录,例如在处理BibTex. 在上面的例子里面,BibTex需要对.bib文件进行独立编译(run BibTex),但是会报错:找不到.bib文件所在目录下面的aux文件。似乎没有办法修改BibTex的设置,所以.bib文件只能和.tex放在同一个目录下面。

(3)工具栏布局丢失问题
TeXnicCenter经常出现丢失已经设置好的浮动工具栏布局,随机让工具栏重设:所有工具栏都重新一行,占据很大屏幕空间。目前没有办法解决。

2009年6月28日星期日

转载西西河: 如何写好科技论文的一些个人建议

如何写好科技论文的一些个人建议

笔者到现在为止在专业期刊中共发表过三十多篇peer review的学术论文,也曾经做过二十次左右的论文审稿人(reviewer)。根据自己的论文写作经验和审核经验,愿意将自己对如何写好科技学术论文 的不太成熟的看法及建议写出来与大家分享,也欢迎大家多多讨论以期共同提高科技论文写作水平。

发表peer review的学术论文,首先要过审核关。显然,如果了解审稿人在审稿过程中的侧重点,那么对我们自己文章的写作无疑是有帮助的。所以,不妨先谈谈我个人的一些审稿经历。
http://www.ccthere.com/article/1555183
在我审核过了文章中,仅仅有非常少量的文章我是认识文章作者的,不得不承认,如果我与文章的某个作者相识,那么我从来没有拒过他们的文章,这更大 的原因是因为我了解他们以前的工作,因此对他们的工作比较信任,另外个人感情因素也起一定作用。比如说,曾经审核过一篇文章,那篇文章的最后作者是与我私 人关系非常好,学术水平也非常高的教授,但是那篇文章写的质量非常差,甚至还有英文写作的问题,按平时的标准是应该拒的,但是只因为那个作者的名字在上 面,(我猜那多半是挂名作者,因为文章的写作风格完全不是那位教授的风格,那位教授既不是通信作者也不是第一二位作者),由于那家期刊(journal) 并不是很有名气,影响因子也不是很高,于是我再三考虑过后,决定给文章的整体评价是一般,然后写个非常具体的意见,建议编辑(editor)此文必须进行 大幅修改(major modification)以后才可发表,在论文修改建议中,我甚至给出了所需要的进一步分析计算的详细步骤。通过这个例子,我想说确实存在这种可能性: 如果你的文章中有比较有名望的教授挂名,你的文章的被接受的机会肯定会相对来说更大一些。

但是对于绝大多数我审核过的文章,我对作者根本就不认识,这时候我的审核标准还是比较统一的。一般说来,审核文章最主要的标准有三个.
http://www.ccthere.com/article/1555183
1,创新性(originality)

一般说来,编辑在找审稿人的时候(我自己也做过guest editor,所以了解这个过程),都是需要自己先浏览一下文章,然后找对领域比较熟悉的并且在领域内有点学术信誉(academic credit)的人审稿,这样就可以一定程度上保证对文章创新性的判断。越是名气大影响因子高的期刊越是强调文章的创新性这一点.影响因子很高的期刊由于 所收稿件比较多,编辑为了提高审核效率会第一时间直接拒绝那些明显质量不高,创新性不够的文章,而根本就不会把文章发给审稿人,省去了费力找合适审稿人的 麻烦.比若说,如果你的论文是有关实验的,那么你的文章中是否介绍了新的实验方法?你的文章是否发现了新的现象?还是更多重复或者遵从(follow)前 人的成果,仅仅对试验步骤作了些简单的修补?如果是后者的话,而编辑恰好又是同领域的专家,他们就很容易判断出来你的工作的创新性的,那么你的文章被直接 据掉也就不奇怪了。
http://www.ccthere.com/article/1555183
具体到我们的研究或者文章上,为了保证文章的创新性,我们做研究前一定要多做做学术文献检索工作(literature search),一定要搞清楚同领域内有哪些问题已经被解决,哪些问题有待解决;一定要找出那些比较重要的文献细读精读;一定要对领域内的专家最新动向有 所了解.而体现在写文章上就是,在写介绍部分(introduction)的时候,索引要写得清楚,全面。千万别小看文章的introduction,内 行看门道,如果你的文章introduction写得好,审稿人就马上能够判断出来你对领域的熟悉程度,他们对你的研究工作就会有一个比较好的第一印象, 审稿人的审核情绪也会有所提高,自然你的文章顺利通过审核的可能性也就大乐。

从我个人经验来说,我在写文章的时候,总是愿意先写正文介绍自己的工作,最后才写介绍(introduction)部分.而在任何可能情况下,我 的文章寄出去前,总喜欢找一位领域内名气大的学术水平高的老教授帮我修改introduction部分。特别是一般自己觉得比较不错的研究文章,在寄给杂 志之前,让同领域的“高人”帮你把把关不失为对自己负责对研究负责的好办法。
http://www.ccthere.com/article/1555183
文章的创新性(originality)当然还体现在文章主体关于研究方法的介绍,不过这里暂时不特别强调这一点。以后有机会单独开贴聊吧.

最后,我刚才提到比较好的期刊(journal)收入的文章,文章创新性(originality)是非常关键的一点.如果你觉得自己研究工作的 创新性不够,那么建议不要直接往顶级刊物上投。要知道投稿也是有学问的,因为如果你经常往某个杂志投稿结果经常被拒,你在那个杂志编辑心目中的学术信誉 (academic credit)就会很快丢失了.这样你下一次如果再想往同样刊物上发文章就更难了。相反你的文章被某个杂志发表的比较多,那么你也会慢慢也会积累起来你的 信誉,有了信誉没准那一天你会被期刊编辑邀请做期刊审稿人了呢.所以我个人主张发文章从选择合适的期刊(jouranl)开始就要慎重。同样的道理,被杂 志选为审稿人也是一样的道理,所以不要总听那些抱怨牢骚的话,不要文章一被拒就怀疑审稿人故意刁难,这种情况有但并不是主流,因为每个审稿人也需要考虑自 己的信誉.况且每篇文章不是一名审稿人说了算的,某位审稿人如果胡乱评文章,那几次以后他不仅没有机会再做审稿人,很可能他辛辛苦苦积累下来的学术信誉也 会丧失的。
http://www.ccthere.com/article/1555183
2,全面性(completeness)

如果文章有一定的创新性,那么第二个重要的判断指标就是文章的全面性(completeness)。这一点比较tricky。我审核过的文章,还 有我自己发表的文章被审核,reviewer多数是在此方面“做文章”。再严谨的研究者也可能会遗漏些自己没考虑到的地方,这时候,reviewer会指 出研究的不足之处,给作者建议让他补充新数据或者对某些结论增加些解释等等,最终reviewer给文章的评语多半是major modification,这种情况对试验和计算方面的研究更常见。也有些情况,文章不足的地方太多,甚至由于不够严谨导致结论“错误”,这时候文章多半 是要被拒的。
http://www.ccthere.com/article/1555183
在你从期刊编辑那里收到所投文章的reviewer comments的时候,一定要仔细查验那些建议或者意见。也确实会有些审稿人不负责任,甚至有可能他们都没有读明白你的文章,给出了比较荒唐 (ridiculous)的评语或者建议,但不管怎样,还是应该多在自己身上找毛病.仔细想想是不是自己文章本身实在是不够严谨,甚至研究中有太多的不确 定因素(uncertainty)?在修改文章时候,一定要认真考虑审稿人的建议并补充新的证明材料.如果文章被拒不要抱怨审稿人吹毛求疵,以我的经验审 稿人不大有可能是因为作者名气不足而故意刁难作者。但是倒是有可能审稿人对于他们自己熟悉的作者的文章尽量多挑毛病,避免直接拒掉,这可能是那些有名望的 教授发文章过程中能够占到的唯一一点"小便宜"了。

但是另一方面,大多数有名望的教授往往更看重自己的名誉,至少我认识的几位美国著名教授(院士),只要文章中有他的名字,在文章投出去之前,他们 都要自己最后亲自审核文章的。他们的审核甚至比通常的审稿人更要严格,而他们修改过的文章,不得不承认文章确实水平高,那么如果你觉得自己的研究确实不 错,如果能找有名望的教授愿意帮你把把关是保证你文章质量的不错的办法。
http://www.ccthere.com/article/1555183
3。写作技巧(writing)

科技论文的写作技巧并不像小说那样要求高。但好的科技论文是可读性很强的,关于科技论文写作技巧,以后有时间会单独开贴于大家探讨.这里有个联结链接出处,大家可以先看看,文章的作者是剑桥大学资深教授,学术水平很高,都是他的宝贵经验,对于我们这种刚开始写科技论文的新手来说借鉴一下绝对有好处。
http://www.ccthere.com/article/1555183
另外,我们千万不要忽视科技论文的写作技巧.因为文章写作技巧对文章的发表与否,和文章发表后的引用情况都有影响。在文章审核阶段,审稿人在审核 文章的时候,如果作者经常出现语法错误,那么几乎是他们最难以忍受的,这表明作者对文章的写作态度就不太端正.给审稿人的印象会非常差,这种情况下审稿人 会对文章的审核更吹毛求疵一些也就不足为奇了。另外,写得比较好的文章,可读性强的文章,在文章发表后能够引起更多数人的注意,相对来说影响力 (impact)也会更大,文章被索引次数当然就会更高。所以在发表文章前最好多修改几遍文章,哪怕是找别人帮助看看语法对自己文章质量的提高也是有帮助 的。

最后,希望大家要正确对待论文被拒.在我个人发表的文章中,就曾经有一篇被拒过.我为了那篇文章前后狠下功夫地做了一年左右的研究工作,当时被拒 觉得很不公平,但是过后想想却觉得"因祸得福".我当时是这样做的,那篇文章被拒后我等了半年多才第二次发表出去,期间又进行了大量进一步的研究,并对原 文进行了大量的修改。结果那篇修改过的文章现在成了我所有文章中被引用次数最多的一篇,几年时间内已经被引用超过百次.所以说,文章被拒的经历并不见得是 坏事,态度端正以后,会把坏事变成好事的,用米卢的帽子上话来说就是“态度决定一切”

2009年6月2日星期二

解决了wanda小鱼的中文乱码问题

wanda小鱼的唐诗宋词文件里面的书名号无法正确显示,所以就变成了乱码,按照Bear博客中的办法,用sed把里面的书名号全删除就可以了:

cd /usr/share/games/fortunes/
sudo sed -ie 's/[[:cntrl:]]\|\[33m\|\[32m\|\[35m\|\[m//g' tang300
sudo sed -ie 's/[[:cntrl:]]\|\[33m\|\[32m\|\[35m\|\[m//g' song100
sudo strfile song100
sudo strfile tang300

用上述命令的时候记得检查单引号,千万别用中文的单引号,不然就报错。

Debian下用iceweasel编写hotmail邮件的问题

Debian由于版权问题,使用了firefox的克隆版本 iceweasel。但是傻瓜hotmail却不认,所以当你用iceweasel写邮件的时候,发出去的信都是空白。今天临睡觉前特意google了一下,找到了问题的原因和解决方法。感谢Steven J老兄的帖子Hotmail does work--badly--with Linux , 按照他给出的说明做就可以了。

2009年6月1日星期一

软件的艺术化

最近关注科研比较多,较少来关心软件技术方面的事情。午饭后路过学生会门口,顺手拿了一张放在宣传品架子上的近期艺术活动介绍的单张。虽然自己是做工程方面的,但是对于艺术,特别是视觉艺术,还是多少有些钟爱的。翻看手里的单张,看到关于瓷器方面的展览介绍,就想到一个问题。工艺艺术最早也是发源于日常用品的装饰效果,渐渐就脱离实用性而独立存在了,比如花瓶和瓷盘的存在往往并不是为了实用目的。软件的发展会不会有一天也达到这个程度。当软件功能的日益完善,可能软件界面给用户的观感可能比功能来说更为重要了。自己也就是在无聊中这么一想,不过这是完全可能的猜想,比如苹果公司的ipod和imac,就是最好的例子。所以推而广之,这个方向还是很值得一想的。

2009年4月27日星期一

Scilab 5.1.1使用感受

使用scilab5.1.1已经有2个星期,总体觉得这个版本不错,但是还存在一些奇怪的问题。第一个奇怪之处是windows版本比linux版本的性能要好很多。我用它做矩阵搜索,一天一夜windows版本可以做2万多次循环,而在debian5 上只能做3000多次。这个性能差异太大了。可能在Linux上的版本没有做好足够的优化。第二,在windows上出现运行中如果异常停止,强行杀掉程序进程则Wscilex进程变成独立进程,必须手工杀掉才行。但总体来说,scilab5.1.1还是很不错的。

2009年4月24日星期五

终于等到了scilab 5.1.1

Scilab是开源软件中替代Matlab的不二之选。我一直用这个东东来做数值计算,平时还用来当计算器,是个小巧方便的家伙。但是从4.1到5.0的升级让我很恼火。现在终于出了5.1.1, 终于让人满意些了。
scilab出了5.1.1版本,让我等了3个多月。应该说scilab从4.1到5.0的升级太让我失望了。首先是体积大了好几倍。4.1才25M,5.0就长到了80多M。但是比比matlab,也没什么好说的,还是苗条太多了。其次,4.1版本的断点设置和调试功能在5.0里面都被去掉了,程序只能靠经验和猜来调试了。这个是最垃圾的升级了。其次就是不稳定,我的程序需要占用较大的内存,run一次没问题,再跑一次就出现栈溢出了。这个错误实在是太低级了。 但是到了5.1.1版本,发现稳定性的问题终于解决了。5.1.1还有一个比较好的地方,就是提供了stacksize('max')函数,可以让scilab尽可能大的利用系统的内存资源。这点比matlab都好。Matlab中反正我没找到这方面的设置。

2009年4月21日星期二

GnuPG在windows下面的问题

今天在xp上重新安装了GnuPG 1.2for windows的版本.但是WinPT一直就无法正常工作。开始以为是WinPT的问题,最后在终端下手工进行gpg命令操作,最终发现问题出在gpg上。 调用了 gpg的 --gen-key命令,结果生产公钥的时候报了一个错,无法写入文件。根据提示,是因为gpg里面对于目录的处理混用了/和\,造成无法正确找到并且打开对应目录下面的文件。而在我重装系统之前,似乎没有这个问题。 我又手工试试,发现windows对于\和/都能正确解析为目录分隔符,但是当他们两个混用的时候就出问题了。 回想起来,之前的确碰到过不少基于minGW的移植程序出这样那样的问题。这个问题很难归咎到底是微软还是具体程序开发人员的问题。所以对于这类基于minGW的移植程序,我建议还是少用为妙。

2009年4月20日星期一

软件廉价之罪

开源软件,免费软件,从短期来看是极大便宜了消费者。但是毕竟作为一种劳动商品而言,他无法摆脱商品的一般规律性。目前过低的软件价格,直接导致了大量的程序开发人员难以温饱而转行,同时也降低了厂商开发的积极性和软件的质量。最近最有趣的现象是软件市场也出现了“劣币驱逐良币“的现象。大量的软件为了盈利,都开始捆绑流氓广告软件。这种风气不光在软件行业,而且是在整个信息资讯行业都弥漫起来了。互联网上基本看不到不带广告的网页。这种盈利模式一旦开头就会彻底驱逐正规的软件。个人觉得这是大众的悲哀。

2009年4月19日星期日

BT都带后门了

前几天从bittorrent下载了bt用了用。今天在无意中发现bt给我的火狐和IE装了一个ask.com的工具栏。更奇怪的事情还在后面,当我的网络出问题的时候, 火狐报错,错误为当我在地址栏里面输入新浪的域名后,这个域名被传给了一个jar文件做为参数而执行。 很明显,bt的安装在火狐中截取了我的网络访问。这样的话,技术上他完全可以过滤我的所有输入和访问,包括我的银行密码。后来查看了ie,同样被装了ask.com的工具栏。

如果不是这次出现了意外断网,我根本不可能发现这个问题。在屏幕的背后,真的不知道有多少恶意的程序在我的电脑上。当大家越来越依赖网络的时候,大家越来越失去隐私和安全。

爱普生墨盒真丢人阿

今天偶然在youtube上看到一个小片子,片子示范了爱普生的墨盒如果报没墨了而且打印出的东西都是糊的的时候,只要把墨盒上面的小电路reset一下,再看就发现明明还有一半的墨水,而且打印出来仍然是正常的。说明爱普生是故意搞小动作让用户去买墨水。真的太黑了。

Google的爪子

最近发现Google服务中有一个网络记录服务,查看了一下自己的网络浏览记录。发现凡是和Google相关服务的浏览都被Google记录了。我个人觉得这是一个很恶劣的服务。虽然这个服务宣扬能帮你找到遗忘的访问历史,但是当你接受协议的时候,你其实就被Google给狗仔了。这其实很侵犯个人隐私。Google虽然可以原则上只记录你的日常行为,但是在技术上要过滤你的邮件,检索你的各类密码都是很轻易的事情。当大家都把微软作为恶魔来对待的时候,我希望大家别忘记了Google,它可能在不远的将来比微软更为恐怖。

2009年4月18日星期六

利用笔记本多媒体键盘的多余键进行一键锁屏

我的HP本本的键盘上有2个触摸感应键, 一个默认用来调HP的帮助文档, 一个默认是用来切换PPT全屏的. 这两个键我重来不用, 今天无聊之际, 我把其中一个指向了rundll32.exe user32.dll,LockWorkStation 命令,这样只要一键我就可以锁屏了. 另外一个键还没想好做什么用. 要不来个一键关机,不过这样有点危险. 不小心碰到了就哭把.

成功用debian代替windowsxp作为桌面

debian出了5的版本,感觉它终于成熟了。我从它的第三个版本开始追随它,但是一直由于桌面和中文的不满意而放弃。只是拿他作服务器来远程使用。这次出的lenny很不错,我的老本本的视频和音频,以及宽频屏幕都自动配置的很好,我还自己很方便就搞定了QQ和skype。真的没需要再回到windows下面了。真是感觉很自由高效。

2009年4月15日星期三

常用软件列表

文档编辑
office 2003
Lyx
Letex+WinED

压缩解压
7zip

聊天
skype
MSN
QQ

字典
金山词霸

股票亏损的补偿原则

假设在一只股票的价格为x时买入,当亏损达a%时止损,则回本需要升幅b%为多少。
x*a/100=x(1-a/100)b/100
b=100a/(100-a)
当a 较小 (<5)b约等于a
当a 比较大, 例如50, 则b=100, 要想翻本必须要盈利为100%才可实现。
如果要求翻本代价小于b/a=120%, 则止损位置a%应该为16.7%.
当要求翻本代价小于105%, 则止损位置应该为a%=4%.

2009年3月18日星期三

该死的山寨移动硬盘盒

上个月在深圳买了两个移动硬盘盒,用来更换我已经用了4年的老三星的盒子。现在山寨东西的确便宜,才30多而已,记得三年前我那个老三星买了80多呢。结果这几天坏事了,两个新山寨版的三星盒子不能同时连在一台电脑上。 估计山寨版本里面用的那个台湾芯片有bug,两个同样的片子用在一起就windows就抽风了。原来那个老三星里面用的可是cypress的片子。真是郁闷。