猴子掰玉米?比较不同版《领域驱动设计》说“不变式”、“聚合”

潘加宇

因为要截几张图,又翻看了Eric Evans《领域驱动设计》的中译本,说一些感想。

《领域驱动设计》的中译本目前有这么几个。

2006年,清华大学出版社首先出了中译本(以下称“清华06版”)。这个版本虽然不是UMLChina译,但译稿经过了我们的审校,所以封面有“UMLChina特别推荐”的字样。

dddcover.png
ddd2006copyright.png

2010年,人民邮电出版社重新翻译出版中译本(以下称“人邮10版”)。这个中译本的翻译和UMLChina无关。我们积极配合出版社做了大力宣传,所以UMLChina的图标出现在封底。

ddd2010.png
ddd2010copyright.png
ddd20102.png

2016年,人民邮电出版社将人邮10版本加了“审校”二字重新出版(以下称“人邮16版”)。人邮10版相对于清华06版,从48元涨到69元,但人邮16版却没涨,依然是69元,赞一个!可惜,“UMLChina”消失了。

ddd2016.png
ddd2016copyright.png

当然,不管中译本出了多少种,都是针对Eric Evans的2003英文版,原版目前为止并没有出新版。

dddeng.png

以往如果我需要看这本书,一般看原版或清华06版(严格来说,是电脑里出版前Word的译稿),之前并未仔细看过其他版本的中译本。人邮版的版式、字体和纸张都比清华06版更讲究,所以我一直自然而然地认为,译文也应该很讲究。

这次想做幻灯想要截几张书里的图,比如,针对这段原文:

dddaggregate_en.png

我找到人邮16版对应内容:

dddaggregate_16.png

红线是我画的。

人邮16版将invariant翻译为“固定规则”,其实这个词的翻译是“不变式”或“不变量”。像人邮出的下面这本书的翻译就是正确的:

adaptivecodecover.png
adaptivecode_en.png
adaptivecode_cn.png

如果说译者觉得“不变式”不好,毅然决然抛开常用译法,一定要译为“固定规则”,也未尝不可,但再细究整句译文就可以发现,译者是对invariant的概念不理解,才导致了乱用词并且曲解了意思。

dddaggregate_162.png

即使把“固定规则”替换成“不变式”也是错的。“满足所有不变式”?那这不变式是谁的?

其实不变式是对象的。

正确的意思应该是,(对象各成员)要满足对象的所有不变式,(聚合各成员)要满足聚合的所有不变式,而不是对象去满足不变式,聚合去满足不变式。(从这一点展开来说,聚合(aggregate)这个概念其实可以不要,聚合就是对象,对象就是聚合。以后不知道有没有人伪创新“聚合的聚合”,“中聚合”、“大聚合”、“超大聚合”。)

关于不变式,下面摘自Bertrand Meyer“Object-Oriented Software Construction(Second Edition)”的页面应该可以帮助理解:

meyerbookcover.jpg
meyerinvariant.jpg

2005-2006年间,Meyer这本书的译稿(不是我译)纸质版在我手上放了半年多。收到机械工业出版社编辑老师寄过来的几公斤重的译稿时,还兴奋地专门发新闻说“中译本要出版了!”。结果,审稿进度缓慢,最后很惭愧地把译稿退还给了编辑(记不清到底退了没有?不要过几年在家里某个箱底看到)。直到现在,还没有出版社出版此书的中译本,以后应该也不会有了。

ooscnews.png

Bjarne Stroustrup(C++)也强调了不变式的重要(https://www.artima.com/intv/goldilocks.html#part3):

stroustrupinterview.png

人邮16版译文中额外加了个原文没有的“分门别类”,译者可能以为锦上添花一下也无妨,结果却又暴露了对概念的不理解,又把意思搞反了。

ddd16relationship.png

分门别类的意思归纳相同特征,相当于泛化,如下:

generalization.png

聚合却是把不同特征聚在一起,如下:

aggregate1.png
aggregate2.png

对于研发部这个“聚合”,可以有不变式:鼓励师人数不得少于程序员和架构师人数之和。

对于鼓励师,也可以有不变式:年龄不超过25岁则重量不得超过50公斤;年龄不超过30岁则重量不得超过52公斤。


注意,人邮16版是以“审校”的名义重出的“第二版”,那是不是人邮10版更差呢?我又花心思找到了其他中译版本。以下是人邮10版的对应内容:

ddd10aggregate.png

人邮10版和人邮16版似乎一模一样,没看出“审校”在哪里。

清华06版的对应译文如下:

ddd06_cn.png

如果不理解原文,可以打开清华06版,在此基础上“参考”并“发展”多好。如果每次“创新”或“更新”都像猴子掰玉米,掰一个丢一个,进步从何谈起?我们现在有很多原地踏步甚至是退步的“伪创新”,原因多是不了解也懒得花精力去了解前人的工作。


书中讲述的的另一个概念Value Objects,原文:

dddvalueobjecten.png

人邮16版出了一个错别字:

ddd16valueobject.png

以下是人邮10版的对应内容:

ddd10valueobject.png

可以看到,这个错误是人邮10版就有的。这个地方,人邮16版又是和人邮10版一模一样,也没有“审校”过来。

清华06版的对应译文如下:

ddd06valueobject.png

至少没有错别字。

不过,大家都把some译成了“某种”……,莫非人邮译者也不是没有参考过清华06版?


我又想到,在“聚合”这一点上其他书有没有类似问题呢?我又翻开《实现领域驱动设计》,Vaughn Vernon 著,滕云 译,张逸 审,电子工业出版社。

iddd.png

类似地方,同样有类似问题。

第10章一开头,原文:

idddaggregateen.png

译文:

idddaggregate2.png

译者看到parent,误以为是“父类”,从而臆想出“对象树”这样的文字。

这不只是看走眼或者英语水平的问题,还有面向对象的基本概念不清楚的问题。

泛化和关联是面向对象的两种基本关系。

泛化表示集合关系,两个类形成泛化,意味着超类的对象集合包含了子类的对象集合,如下图:

generalization1.png

而关联表示个体关系,两个类形成关联,意味着一个类的对象个体组装了另一个类的对象个体,正是因为是个体,才有1对多,多对多等多重性。如下图:

aggregate3.png

例如,自然语言"人有男有女"说的是泛化关系。因为意思不是一个人的个体组装了若干男人个体和若干女人个体,而是说人的集合包含了男人的集合和女人的集合。但是,自然语言"人有手有脚"说的却是关联关系。因为意思不是人的集合和手、脚的集合有包含关系,而是说一个人的个体组装了若干手和脚的个体。您可以自行体会一下“人有车有房”和“人有高富帅有屌丝”的区别。

聚合实际上就是关联的一种,但Eric Evans选择这个词其实并不恰当,更恰当的词是组合(composition)。

我们来看刚才译者的翻译错在哪里。

首先,可能把聚合当成了泛化,所以有“父类”的说法。

其次,受“父类”的误导,又混淆了类和对象的概念,所以产生了“对象树”的说法。先不说原文本来就没有“树”的字眼,“对象树”的说法本身就是错的。

译者可能以为自己说的是这样的树:

relat1.png

但是这样的树代表的意思是:

relat2.png

这是“类(集合)”的树,不是“对象(个体)”的树。

原文用的词是graph,就是object graph的那个graph。这个啥意思,我想就不用多说了。

针对《实现领域驱动设计》的翻译错误,我还曾经写过一篇文章批评>>


weixinpanjiayu2.jpg