silverghost

世界可以想象,世界可以创造

Avatar

Unit Testing versus Functional Testing

Unit Tests are written from a programmers perspective. They are made to ensure that a particular method (or a unit) of a class performs a set of specific tasks.

Functional Tests are written from the user's perspective. They ensure that the system is functioning as users are expecting it to.

ref. h ttp://www.softwaretestingtricks.com/2007/01/unit-testing-versus-functional-tests.html

Buzzwords aus meiner Diplomarbeit

关于Ubuntu 用latex写论文

刚刚结束Studienarbeit,论文用latex在Windows下proTeXt编写,总体来说还很方便,但是安装和配置过程有点费劲。 在Ubuntu下总体来说比较方便,但是可能对刚刚初用Latex的人有点难度,首先做下Ubuntu的安装更新,基本的安装过程很简单

sudo apt-get install texlive


建议安装

sudo apt-get install texlive-latex-extra


如果支持不同的语言(比如德语)

sudo apt-get install texlive-lang-german 

之后为了方便起见在这里贴一段Makefile, 作者是Richard Membarth

#
# Makefile for pdfs
#

TEXINPUTS:=.//:$(TEXINPUTS)

ifeq ($(shell echo -e x), -e x)
    ECHO = echo
else
    ECHO = echo -e
endif

TEX = thesis.tex
BIB = #literature.bib
BLG = $(BIB:%.aux=%.blg)
PDF = $(TEX:%.tex=%.pdf)

all: $(PDF)

$(PDF): *.tex $(BIB)
        @$(ECHO) " *\n * pdflatex: $(TEX) > $@ \n *"; \
        ( \
    TEXINPUTS=$(TEXINPUTS) pdflatex -shell-escape $(TEX); \
    if grep -q "There were undefined references." $(TEX:.tex=.log); \
        then \
          bibtex $(TEX:.tex=); \
          TEXINPUTS=$(TEXINPUTS) pdflatex -shell-escape $(TEX); \
        fi ; \
    if grep -q "There were undefined references." $(TEX:.tex=.log); \
        then \
          TEXINPUTS=$(TEXINPUTS) pdflatex -shell-escape $(TEX); \
        fi ; \
    while grep -q "Rerun to get cross-references right." $(TEX:.tex=.log); \
        do \
          TEXINPUTS=$(TEXINPUTS) pdflatex -shell-escape $(TEX); \
        done; \
        $(ECHO) "\n\n *******************************************************************************"; \
        $(ECHO) " *                                                                             *"; \
        $(ECHO) " *   WARNING SUMMARY                                                           *"; \
        $(ECHO) " *                                                                             *"; \
    grep -i "Warning" $(TEX:.tex=.log); \
        $(ECHO) " *                                                                             *"; \
        $(ECHO) " *******************************************************************************\n"; \
        )

.PHONY: clean
clean:
        @$(ECHO) " ** Remove automatically generated files " ;\
        rm -f *.out *.bbl *.blg *.tpt *.toc *.log *.aux *.idx *.nav *.snm *.vrb *.backup *~ *.table *.gnuplot;

distclean: clean
        @rm -f $(PDF);


文件名 Makefile
生成PDF 用 make
删除临时文件 make clean
删除PDF文件 make distclean (make之前要运行一遍)

Buzzwords from my student thesis

Made by Wordle


用SBT创建Scala project

在网络上有非常多的观点关于建立Scala项目时用Maven还是sbt,如果你使用java很长时间一定很喜欢Maven而不是用Ant,但是如果你想创建Scala项目,那sbt一定是个不错的选择,因为他因为他就是为此而生,从而有很多功能和特点去支持这个编程语言.

现在先介绍一下如何安装sbt:

下载 sbt-launch.jar
然后拷贝这个文件到你系统的bin文件夹下,比如我:
zhichao@desktop:~$ sudo mv sbt-launch-0.7.7.jar /usr/local/bin/sbt-launcher.jar
创建脚本文件叫sbt,内容是这样的
echo “java -Xmx512M -jar /usr/local/bin/sbt-launcher.jar \”\$@\”" | sudo tee /usr/local/bin/sbt
执行赋予文件
sudo chmod +x /usr/local/bin/sbt
如果你正确按着上面说的去做能得到下面的显示:

zhichao@desktop:~$ sbt
Project does not exist, create new project? (y/N/s)

为了创建一个新项目,一个文件夹应该被创建向下面所示:


zhichao@desktop:~/Documents/HelloWorld mkdir HelloWorld
zhichao@desktop:~/Documents/HelloWorld$ cd HelloWorld/
zhichao@desktop:~/Documents/HelloWorld$ sbt
Project does not exist, create new project? (y/N/s)

按着提示输入项目的基本属性


zhichao@desktop:~/Documents/HelloWorld$ sbt
Project does not exist, create new project? (y/N/s) y
Name: HelloWorld
Organization: de.mobiStudio
Version [1.0]:
Scala version [2.9.0]:
sbt version [0.7.7]:
Getting net.java.dev.jna jna 3.2.3 ...
:: retrieving :: org.scala-tools.sbt#boot-app
	confs: [default]
	1 artifacts copied, 0 already retrieved (838kB/15ms)
Getting Scala 2.7.7 ...
:: retrieving :: org.scala-tools.sbt#boot-scala
	confs: [default]
	2 artifacts copied, 0 already retrieved (9911kB/25ms)
Getting org.scala-tools.sbt sbt_2.7.7 0.7.7 ...
:: retrieving :: org.scala-tools.sbt#boot-app
	confs: [default]
	17 artifacts copied, 0 already retrieved (4379kB/41ms)
[success] Successfully initialized directory structure.
Getting Scala 2.9.0 ...
:: retrieving :: org.scala-tools.sbt#boot-scala
	confs: [default]
	4 artifacts copied, 0 already retrieved (20442kB/45ms)
[info] Building project HelloWorld 1.0 against Scala 2.9.0
[info]    using sbt.DefaultProject with sbt 0.7.7 and Scala 2.7.7
>

至此项目已经被创建好了,你可以退出(ctrl+c)创建过程,因为我们需要至少一个类来完成编译.


> run
[info]
[info] == copy-resources ==
[info] == copy-resources ==
[info]
[info] == compile ==
[info]   Source analysis: 0 new/modified, 0 indirectly invalidated, 0 removed.
[info] Compiling main sources...
[info] Nothing to compile.
[info]   Post-analysis: 0 classes.
[info] == compile ==
[info]
[info] == run ==
[info] == run ==
[error] Error running run: No main class specified.
[info]
[info] Total time: 0 s, completed 19 May, 2011 3:39:02 PM
>



zhichao@desktop:~/Documents/HelloWorld$ cd src/main/scala/
zhichao@desktop:~/Documents/HelloWorld/src/main/scala$ gedit HelloWorld.scala



object HelloWorld {
  def main(args: Array[String]) {
    println("Hello, World!")
  }
}

接下来我们应该看到如下提示,


zhichao@desktop:~/Documents/HelloWorld$ sbt run
[info] Building project HelloWorld 1.0 against Scala 2.9.0
[info]    using sbt.DefaultProject with sbt 0.7.7 and Scala 2.7.7
[info]
[info] == compile ==
[info]   Source analysis: 1 new/modified, 0 indirectly invalidated, 0 removed.
[info] Compiling main sources...
[info] Compilation successful.
[info]   Post-analysis: 2 classes.
[info] == compile ==
[info]
[info] == copy-resources ==
[info] == copy-resources ==
[info]
[info] == run ==
[info] Running HelloWorld
<strong>Hello, World!</strong>!
[info] == run ==
[success] Successful.
[info]
[info] Total time: 6 s, completed 25 Nov, 2011 13:45:06 PM
[info]
[info] Total session time: 7 s, completed 25 Nov, 2011 13:45:06 PM
[success] Build completed successfully.
zhichao@desktop:~/Documents/HelloWorld$

至此对sbt的安装和创建已经完成,我们有两种选择,一个是继续用Editor编程或者选择IDE开发,我的选择是将项目引入到Eclipse当中, next….

无为

Als die Nazis die Kommunisten holten,
habe ich geschwiegen;
ich war ja kein Kommunist.

Als sie die Sozialdemokraten einsperrten,
habe ich geschwiegen;
ich war ja kein Sozialdemokrat.

Als sie die Gewerkschafter holten,
habe ich nicht protestiert;
ich war ja kein Gewerkschafter.

Als sie die Juden holten,
habe ich geschwiegen;
ich war ja kein Jude.

Als sie mich holten,
gab es keinen mehr, der protestierte.
---Martin Niemöller(1892-1984)

中譯

當納粹來抓共產主義者的時候,
我保持沉默;
我不是共產主義者。

當他們囚禁社會民主主義者的時候,
我保持沉默;
我不是社會民主主義者。

當他們來抓工會會員的時候,
我沒有抗議;
我不是工會會員。

當他們來抓猶太人的時候,
我保持沉默;
我不是猶太人。

當他們來抓我的時候,
已經沒有人能替我說話了。
---------------------------------------------------------------------------------------------------------
曾经有一位横行于天下而视人为草菅的中国人(至少说国语)说过一句话 "闷声发大财"其实这句话说的很对,只是大多数人没有听明白, 他是想让我们闷声,他们发大财. 至少我们可以嘴上不说,但是我们一定要做。行动上表示不满这个比逃离现实会更有作用.

回国感触

虽然这次回国时间不长,但是每天都在陌生与熟悉之间徘徊,让我感触颇多。
首现,历经将近一天的飞机旅行和转机,我终于赶到了伟大的首都北京,大学同学开车接机,刚下飞机,雄伟壮丽的首都机场彻底让我震惊,望着机场中下飞机的乘客们和幅员辽阔的机场,我的感觉就像正在走进足球场的运动员,跟在法兰克福飞机场那拥挤的人流形成了鲜明的对比,我连取个行李都要做轻轨,NB。
坐上同学的汽车开出机场,我彻底被灰蒙蒙的天空给震撼了,还好,现在还不用戴面具。阔别已久的收费站,多么亲切的收费员的制服。同学骂了一句"真贵",我们开上了高速,同学跟我说"戒严,封路",绕路,迷路。到了旅店,前台服务员告诉我可以刷卡,太好了,终于用上Master卡了,但一顿折腾后,大堂经理过来跟我说,只能用带“银联”标志的master卡,无语,同学垫付。
(此后用文言)速办手机卡跟家里联系,联通索身份证,无,欲以护照,联通说,外国人可以,但国人只能用身份证,我曰,无,答,回家拿去。同学出其身份证,手机卡摆平。 北京几日于动车归家,忐忑不已,但感慨动车内连厕所都跟德国的一样,怀疑德国鬼子抄袭我国技术至于此。驶于途,厕所求救警报突然响起,行人无动于衷,愈10分钟,吾怒,奔逾2节车厢,见列车员热聊手机甚欢。怒曰,求救信号响愈10分,为何无动于衷,答,没听见。列车员随吾至于厕所,原一老妪不知如何开门被困于内,虚惊一场。随行一男骂曰:"是不是死在里面你们也不过来"列车员至于惘闻。
至于哈尔滨,见家人,行于酒肉间,次日询问银行卡密码,知,询问密码乃挂失也,吾必身份证与手机号码给之方得,银行工作人员用扩音喇叭当众将吾之手机号码重复三次,吾怒,问何故,答约,为了安全。吾甚疑惑,为孰人之安全?
购物,见友,甚快,将别,又行于火车至北京,卧铺,将至,一男子神经病发作,殴打同行之人,吾与众合力将其殴倒,逾10分之久不见警察前来,用被绑病男,随后列车员与乘警现于面前,询问吾等身份证号码,众人皆怒。
遂飞机回于德国。
总结,朋友家人过得很好,物价偏贵,连哈尔滨都开始堵车,我家房子竟然也涨价。期待下次回国

为了忘却的纪念-动车事故

其实写博客一般来说都是要记录一下个人的最近状况,但是最近闹得沸沸扬扬的高铁事故似乎渐渐趋于平静,渐渐近似会被人淡忘,所以出来说两句,不为别的,只为纪念死难者.

如果说人的本性是善于遗忘,那么记载历史则会唤醒沉睡的记忆,如果说悲伤可以随着时间的流逝渐渐淡忘,那么镌刻的碑文则会让人永远缅怀.但是你们的离去没有历史的记忆,没有石碑的永铸,伴随你们的是无力的挣扎和让人做呕的谎言.你从桥上重重的坠落,没有运动健儿的身姿,却比那些要先感谢国家再感谢父母的运动员们更猛烈的摇撼我们的心灵,他扯碎我们一切的幻想,撕破我们良知的底线.

残骸可以被掩埋,真想可以被遮掩,但良知不会泯灭,纪念却不能被忘却,你们离开的我们,留给我们的是悲伤,是思考,是勇气,还是恐惧,这一切的所有将被时间证明,而不是被时间冲刷。

别了,无论是35还是40,你们仅仅是被掩埋的真相,但这真相的背后,却是我们对你们的哀思,沉默是为了忘却的纪念,而不是忘却

中国医疗系统之我见

最近在德国学习医学计算机课程,方向是Informationssysteme,中文是医疗信息系统,可能国人对我们国家的神圣医疗体系都非常崇拜,但是具体深入的概念一般都停留在『钱』这个俗不可耐的东西上,所以我来简单介绍和评论一下德国和中国在医疗信息系统领域的诸多区别。

1『钱』

看病要花钱,在国人眼里可能是天经地义的事情,而且成天有人抱怨医药费太贵,医生态度差或者没有救死扶伤之品德等等,医疗矛盾频频发生,医患问题逐渐成为国内的主要社会问题之一。但是,对比国外,我们国家的一般医疗费用(挂号,开药等等)或者说特殊医疗费用(手术)在人均收入等前提的情况下,基本可以说便宜甚至在一些高科技应用医疗领域我们国家的整体医疗费用低于国外同比费用,在德国一个病人在医院每天的平均费用是2500欧元,在中国据我了解可能是2000元左右(国家没有准确的数据,仅仅是个人经历的数据),无论是怎样中国的整体病人的医院消耗费用并不贵。但是,国外和国内唯一的不同就是医疗费用在国外是保险公司承担,而在国内很大一部分是由患者来承担,并且患者对医疗费用的支付上了如指掌。

2 医生道德问题

其实说中国医生道德有问题的人大多数国人的感觉诱因是由一个非常简单的逻辑来得到的,就是我花钱没有买到我应该得到的服务,甚至被医生像商品一样对待,推销药品,甚至治死。我可以不幸的告诉大家,中国医生做的跟外国医生是一样的事情,也就是说全世界的医生都这么干,只不过问题又一次回到上一个题目上来,因为中国的患者承担医药费,所以能得出这种结论的只有中国人,而外国人对医生的道德仅仅是由对待患者的态度上来判断,至于医生在患者身上挣到钱的这种感觉只有保险公司能感觉到,患者对自己病情的产生费用毫不知情。

3 医疗信息系统

我看过国内的一些对医疗信息系统的一些文章,我的感觉一个很大的问题是大多数中国医生或者说医院把这个系统当作办公自动化系统来使用,okay,这个功能没错确实是有这个功能,但是更重要的是这个系统的核心功能是提高各个医疗部门之间的合作效率和整合能力,核对和结算医疗费用,归档病例,提供信息检索,辅助医学研究和医疗决策,并观察医疗决策的作用。所以更让大多数人失望的是,医疗信息系统在传统医疗文件管理方式相比,没有进步多少,有点仅仅是提供快速检索功能,但这个功能仅仅用于医疗研究领域,在治疗领域没有任何帮助,而且在结算领域反而会给国人患者带来压力,因为这样引进或者部署这种系统,会让患者承受更高的医疗费用。换句话说,引入医疗信息系统对主要由患者承担支付只能的环境下,对患者来讲绝对是灭顶之灾。

所以从上述三点来看,对患者来讲引入适当的保险机制的必要性是显而易见的,也就是说保险公司来决定是否来承担这部分患者的一直承担的费用,将患者从医疗结算领域剥离是非常必要的,记住是完全剥离,如果让患者仍然知道每笔医疗的具体费用,甚至让患者先行支付,之后再采取报销的方式,医患问题是无法解决的,因为这样无疑在原有的基础上引入了两个麻烦,一,患者是否有能力现行支付高额的医疗费用,二,保险公私是否会履行支付(报销)义务。记住引入保险公司的目的是避免患者在医疗结算领域所承受的诸多支付问题,而不是让支付问题复杂化。

XML Parser 语法分析器简介

语法分析(英:Syntactic analysis,也叫 Parsing)是根据某种给定的形式文法对由单词序列(如英语单词序列)构成的输入文本进行分析并确定其语法结构的一种过程。

语法分析器(Parser)通常是作为编译器或解释器的组件出现的,它的作用是进行语法检查、并构建由输入的单词组成的数据结构(一般是语法分析树、抽象语法树等层次化的数据结构)。语法分析器通常使用一个独立的词法分析器从输入字符流中分离出一个个的“单词”,并将单词流作为其输入。实际开发中,语法分析器可以手工编写,也可以使用工具(半)自动生成.* wiki

XML语法分析器解析XML文件,并提供其中所载的信息(即Element,Attribute等)并且作进一步处理。

XML语法分析器有两个重要的组成标准。首先是他们验证正确性部分, 第二,提供访问XML文档的接口(SAX或DOM)。这两个组成部分组成的语法分析器很自然有四种可能性,即验证和非验证的SAX解析器和验证和非验证的DOM解析器。

第一条标准,即验证和非验证,这是很容易解释的。一个XML文档是否能被有效检查验证, 是由DTD规范。因此,一个DTD这是绝对必要的。除此之外,良好DTD文档格式也是非常重要的。一个非验证解析器只检查XML文档是否遵循XML规范。在这种情况下,DTD不是必要的, 即使存在也无所谓. 由于一个验证文档分析器是非常耗时,所以应该尽可能避免,所以通常情况下我们用其他方式来验证文档.

第二条标准是通过接口对文件的访问, 即DOM和SAX.

SAX

SAX 的名字是 Simple API for XML, 他是在 XML-DEV Mailing List中诞生的,在1998年5月11日发布1.0版本,SAX是“基于事件”,表示当读到特定的XML结构时候(例如 Element, Attribute等等)就会触发结果,当然在Warning和error的时候也会随之触发相应的结果,开发者可以根据自己定义的事件处理方式独立的输出和处理各种结果。

举个例子

<zitat>
Drum prüfe wer sich ewig bindet, ob sich nicht was Besseres findet.
</zitat>

语法分析器可以触发如下事件

开始Tag
文本
结束Tag
DOM

DOM的名字是Document Object Model,它是由一颗以Element为结点的语法树结构所构成,输出的结果是遍历这颗树的所有结点

<buch>
<titel>Galgenlieder</titel>
<autor>
<vorname>Christian</vorname>
<name>Morgenstern</name>
</autor>
</buch>

结点树结构如下

由此可见如果XML文本结构越复杂,构成的树形结构越巨大,相应的所需要的存储空间要比SAX大得多,这也就是DOM-API的缺点所在

对比DOM和SAX

SAX要快速和简单,当然也有很严重的缺点,就是没有对象模型,即没有什么层次结构的存贮关系,所以SAX所应用的领域就是一次性读取文档,从而得到结果

而DOM要慢得多,但是提供了Element之间的树形结果,可以对其进行适当的操作,所以DOM适合交互式的XML文档读取或者XML文档之间存在一些层次关系的梳理方式,但是不要忘记,DOM是需要大量的存贮空间作为支持。

read_more

更多网志请见归档分类