C_and_CPP 版 (精华区)

发信人: seaboy (浪小), 信区: C_and_CPP
标  题: Contracts, Promises, and Mere Semantics 
发信站: 哈工大紫丁香 (2003年06月24日00:17:45 星期二), 站内信件

Contracts, Promises, and Mere Semantics 
taodm翻译

-------------------------------------------------------------------------------
-

和大多数日子一样,我开始了那天的工作-在我的方形房间内,端着新鲜的咖啡,在开始
写代码前,正收着早上的email。很奇特,它这天,Guru没有突然出现在我身后。实际上,
我无意中听到它发生在另外一个人身上。 

我正坐在书桌前安静地工作着,而且听到附近的同事们击键的时间,这是声音传来。 

“时间到了,”Guru说,“谈些事吧。” 

我习惯性地跳了起来。我四处寻视了一下,但Guru并没站在我身后。我接着听到隔壁房间
传来椅子的吱吱声-是Kerry,我们组聪明而又令人讨厌的新人,从他椅子上跳起来。她正
和他在一起。我怀疑他能持续多久;Guru以最开头几个月内吓跑绝大多数的新人而著称,
根本等不到转正。Kerry已经表现为早期的崩溃症状。我估计他将只能再坚持几个星期了。
 

我怀着稍微的内疚偷听着: 

“鲍伯告诉我,我的新代码中有一个问题……”我听到Kerry开始反抗。 

“是吗,我的孩子?”我能回想出她的眉毛翘起来,向我笑着的样子。 

“嗯……是的。是关于编码规范的事,我将自己搞定它……” 

我听到了书合上的声音。Guru肯定已经合上了她带的“砖头”。我懒得猜她今天带的是哪
本。“告诉我,年轻的,”我听到Guru对Kerry说,“我们的编码规范说什么了?说吧。”
 

“嗯……他们就在这里。”在Kerry击键的同时,我也悄声地调出同一文件并找到他正背诵
的位置。这是其中的一部分: 

当申明参数类型时,最好遵循传统的C++接口惯用法: 

如果实参需要被更改,传指针。 
如果实参不被更改,传值。 
“我没这么做,所以鲍伯指出它。就是这么多。这是对的。这是对的;我将修改;真的,
”Kerry说完了,听起来很紧张。 

有一个停顿,我在猜测Guru是在微笑或皱眉。最后,她说:“照他的话做……就现在。更
新代码,但别chek in。而是把更新过的代码给鲍伯,让他查看,并让他自己使用,然后等
待。” 

“等候?……为什么?”Kerry问。 

这次我确定Guru在微笑。“只需等待,徒弟,”她说道,然后我听到了纸的沙沙声和后退
的脚步声。 

表演结束,我想,于是回去工作。但是最精彩的部分总要上演的…… 


-------------------------------------------------------------------------------
-

几个小时之后,我正狂写代码时,听到Kerry被叫到鲍伯的办公书桌,虽然稍微有些远,但
还没远到让我听不见鲍伯狂训Kerry的声音。 

又过了一会儿,鲍伯似乎训够了,Kerry被放了回来,孤独地 (我想)回到他的房间。当他
坐下时,椅子吱吱地响了一下,然后又变得寂静……但没维持多久。 

大约五分钟之后,又次传来Guru的声音,Kerry的椅子又吱吱响了一下(或是Kerry发的?
他已经习惯在Guru出现时发出吱吱声),又一次的对话: 

“关于C语言为什么是烫手的,”Guru突然说道,“而猪是否有翅膀。”我在笑后面一句话
,知道她可能在说鲍伯。 

(吱吱声)“我……我跟鲍伯说了……” 

“的确,你这么做了,孩子,越过整个建筑我都能听到,”传来Guru柔和的声音。又传来
一声书本很快合上的声音。“而他说了什么?” 

“我的代码一定是错的;它让他代码不能工作了,”Kerry结结巴巴的。“但是我不知道我
做错了什么。我就是按他所说的做的!我也就是按编码规范说的做的!” 

“啊,”-我眼前浮现出Guru锐利地微笑-“但它们是同一回事。因为鲍伯是制订这部分
编码规范的人之一。” 

“……他……他是?” 

“哦,是的。他确实是,徒弟。这也就是编码规范发生错误的原因。” 

“错误?” 

“那对C++惯用法而言是错误的,”她继续说道。 

“虽然,它对于没有'引用'的C语言是正确的。” 

“但是……如果是错的,他们为什么不更新?” 

“我们的新经理,Pete Williams,过于信任鲍伯而看不清实际需要,”她叹息道。“他的
前任也没有这么做。于是,编码规范并不正确。C++惯用法更象这个……”我听到了书写笔
在白板上的吱吱声,这是我后来在白板上看到的: 

当申明参数类型时,最好遵循传统的C++接口惯用法,除非它不合适: 

如果实参需要被改变,传非const的指针或引用。 
如果实参不被改变,传const的引用,或在拷贝开销很小时传值。 
“这样的陈述比较接近事实,”Guru总结了一下,“但是,徒弟,你必须注意'最好'和'除
非'这两个词。这只是惯用法。不是教条。它不是没有例外的。” 

“嗯……是的。没问题。鲍伯说,它适用于他试过的每件事物,除了……” 

“auto_ptr对象,”Guru点点头,替他说了出来,我听到她继续在白板上写着。 

Kerry发出了惊讶的声音。“你怎么知道的!鲍伯告诉你的?你看见的?” 

“我就是知道。我不需要看见。”她继续在白板上的写着,而这里是我几分钟之后看见的
: 

template<typename T> 

void Mutate( T* byPointer ); 

template<typename T> 

void Mutate( T& byReference ); 

template<typename T> 

void LeaveAlone( const T* byPointerToConst ); 

template<typename T> 

void LeaveAlone( const T& byReferenceToConst ); 

template<typename T> 

void LeaveAlone( T byValue ); 

“想一下这个例子,然后回答:对于哪种类型的T,函数的名字是名副其实的?徒弟!”她
说道。 

我不知道她说的是我,直到我听到一种不同的啪嗒声,一块橡皮从我头上反弹开去。然后
我很快反应过来,揉了揉头,加入他们。 

“嗯?什么?” 我嘟囔了一句。“我正忙着工作。” “实际上你正专心于竖着耳朵。”G
uru眯起眼睛一会儿,假装烦恼, 然后我看见她闪烁的目光。放下书写笔后,她又打开她
的厚书,将头发挂于耳后,微笑着走开了。“我的徒弟将会解释的,我的孩子……” 她的
分别语从肩头飘来,就在她转弯消失的那瞬间。 

我摇头咧嘴而笑。什么行为!但Kerry古怪地看着我,我怀疑也许他还没开始把我和Guru同
归在“神奇人士”之列。我发现我不会介意的,如果他这么做了的话;这给了我一个有趣
的启示。 

“年轻人,”我微笑着说道,一认识到我刚说了什么,就笑得更欢了,“当你传递一个aut
o_ptr是,会发生什么?” 

“嗯……噢!”很清楚,Kerry已经明白了。“传递了所有权!她说的是这个意思吗?” 

“是的,”我同意。“你已经明白了。而同样事还发生在所有会转移所有权类-顺便提一
句,其典型特征是在拷贝构造函数的形参上使用非const的引用。这就是你要的答案:传值
通常意味着你不会碰源对象,除了auto_ptr,对它含义正相反-并且更差,因为不但修改
了源 auto_ptr,还将它置为了NULL。而传指针常意味着准备修改源对象,除了auto_ptr,
对它含义正相反-你正在避免修改它。对于auto_ptr,传统的惯用法正干着坏事。而这正
是基于通常的惯用法的代码,例如容器对它们所包容的对象作的假设,不能和auto_ptr协
同工作的原因。但不只是对于auto_ptr;对所有在拷贝时进行所有权传递的类都是这样。
总要特别留心在拷贝构造函数中的非const引用参数;那就是你通常会遗漏的致命之处。”
 

“现在,”我一边走一边让我的声音飘向身后,“我必须回去继续我的沉思了。”我到达
走道末端,转了个弯,刚从他视野中消失,就再也忍不住得发出了吃吃地笑声。 


-------------------------------------------------------------------------------
-

[参考文献] 
[1] H. Sutter and J. Hyslop. “Conversations: A Midsummer Night's Madness,” 
C/C++ Users Journal C++ Experts Forum, August 2002. 
 
--
欢迎到C_and_CPP版讨论相关问题。

※ 来源:·哈工大紫丁香 bbs.hit.edu.cn·[FROM: 202.118.239.80]
[百宝箱] [返回首页] [上级目录] [根目录] [返回顶部] [刷新] [返回]
Powered by KBS BBS 2.0 (http://dev.kcn.cn)
页面执行时间:3.981毫秒