2012年5月23日星期三

操作符重载中的一个语言设计谜题

This article is translated from Andrew Koenig's blog, if there is any
copyright issue, please contact me, I will remove it as soon as
possible.
原文作者:Andrew Koenig
原文地址:http://www.drdobbs.com/blogs/cpp/240000124#

在上周的文章(关于参数依赖查找的一篇个人笔记)中让我想起早期C++中的一个问题。这问题的解决方案是一条没多少人知道的规则――但是如果没有这条规则的话,很多代码都没法正常运行。
考虑一个表达式a + b,a和b都是类的对象。编译器将其处理为a.opertor+(b)或者operator+(a,
b),然后将每种处理的各种可能性作为一个很大的集合,最后从中来决定如何重载 + 操作符。
函数的重载决议即找到一个唯一的可能函数,其严格的比其他任何一个都要好。更进一步说,即找到一个函数,至少其中的一个参数的匹配比其他的函数都好,同时别的参数的匹配不比别的函数差。比如:

void f(std::string, int);
void f(std:;string, double);
f("foo", 42);

在这里,重载决议将选中第一个函数,因为对于42,int是比double更好的匹配,而对于另一个参数,两个函数都需要用户定义的类型转换。可是,如果我们写下:

void g(std::string, int);
void g(const char*, double);
g("foo", 42);

函数调用将变成模棱两可的,因为对于第一个函数g,第二个参数的匹配度更好,而第二个函数g的第一个参数匹配度更好。
接下来,让我们把例子搞复杂一点点

struct Thing {
void operator+(std::string);
};
void operator+(Thing&, const char*);
Thing t;

然后我们来考虑下对于表达式t + "s"都发生了什么。这个表达式可能被解释为t.operator+("s")或者operator+(t,
"s"),所以编译器必须决定哪一个更好。在两种情况下,左边的参数t的类型都是Thing,所以仅从第一个参数没有理由认为一个函数好于另一个。可是成员形式的operator+需要将第二个参数转换为string,这就意味着非成员形式的operator+能更好的匹配第二个参数。因此,编译器将选择非成员形式。
这一次,我们把例子再搞复杂一点

struct Blog : public Thing { };
Blob b;

然后来看看表达式b + "s"。这给予了你一次扮演语言设计者的机会:看看你是否能搞明白为什么最明显的解释表达式的方式在这里遇到了麻烦,然后再看看你是否能找到一条简洁的语言规则来避免这个麻烦。
我将在下周揭晓答案

2011年4月7日星期四

my life rate

This Is My Life, Rated
Life:
6.6
Mind:
5.7
Body:
6.7
Spirit:
4.8
Friends/Family:
5.7
Love:
5.5
Finance:
8.1
Take the Rate My Life Quiz

2011年3月12日星期六

找房归来

再一次的搬家找房.2400一个月.在上海就是这样.赚的那点钱全贡献给房东了.这次合租的是女朋友的一个老乡.89年的,差不多就是90后了.恍惚间发现真的是不年轻了.想起up to air里男女主角带着飞的那个刚工作的小女孩.

2011年2月9日星期三

2011年计划

闲着也是闲着,也算是定个年计划。年末回顾下,看看能完成多少。

首先是把刚买的那三本程序书搞定两本先,深入理解计算机系统,算法导论。

经典算法都用C++实现一遍

Linux编程入门

学会python还有haskell

C++模板就更不用说,这个拖了很久了

争取出国旅游一次。

减肥。目标bmi22

2010年9月13日星期一

转:谁分配谁释放

原文链接:http://chengwu2003.spaces.live.com/blog/cns!FC65A74BE5AB6D03!227.entry

在《Windows核心编程》第19章有一段话,

必须注意的是,单个地址空间是由一个可执行模块和若干个D L L模块组成的。这些模块中,有些可以链接到静态版本的C / C + +运行期库,有些可以链接到一个D L L版本的C / C + +运行期库,而有些模块(如果不是用C / C + +编写的话)则根本不需要C / C + +运行期库。许多开发人员经常会犯一个常见的错误,因为他们忘记了若干个C / C + +运行期库可以存在于单个地址空间中。请看下面的代码:

VOID EXEFunc() {
    PVOID pv = DLLFunc();
    // Access the storage pointed to by pv...
    // Assumes that pv is in EXE's C/C++ run-time heap
    free(pv);
}

PVOID DLLFunc() {
    // Allocate block from DLL's C/C++ run-time heap
    return(malloc(100));  
}

那么你是怎么看待这个问题的呢?上面这个代码能够正确运行吗? D L L函数分配的内存块是由E X E的函数释放的吗?答案是可能的。上面显示的代码并没有为你提供足够的信息。如果E X E和D L L都链接到D L L的C / C + +运行期库,那么上面的代码将能够很好地运行。但是,如果两个模块中的一个或者两个都链接到静态C / C + +运行期库,那么对free函数的调用就会失败。我经常看到编程人员编写这样的代码,结果都失败了。

为什么包含这段代码的EXE和DLL不能静态链接,而且任何一个模块都不能静态链接?原因如下:

在VC的C运行库中有一个全局句柄_crtheap,malloc和free都是在这个句柄上使用HeapAlloc和HeapFree来分配释放内存的。如果所有模块都使用动态链接,那么进程空间中只载入一个C运行库,也就只存在一个_crtheap。反过来,只要有一个模块静态链接了C运行库,那么运行库中的全局变量将会被复制一份到该模块中,这样就存在两个_crtheap,进程初始化的时候就会调用HeapCreate创建两个不同的堆,很明显,在DLL的堆上分配的内存拿到EXE中用HeapFree是释放不了的,将会引发内存访问异常。所以,谁分配就应该谁释放,因为我们不是任何时刻都很清楚库函数的资源分配规则。

2010年5月20日星期四

how to write a seal/final class via C++


template <typename T>
class sealClass
{
    friend T;
private:
    sealClass(){};
    ~sealClass(){};
};

class UnInheritable: virtual sealClass<unBase>
{
};

There are no class can inherit form class UnInheritable

2010年2月22日星期一

John的个人秀——Lost Final season E04

剧名:The Substitute

本集基本就是一场撤撤底底的Locke个人秀,同时Sawyer华丽的做了一次绿叶。

洛杉矶,Locke回到家,家里等着他的是自己的未婚妻Helen,还记得她吧,就是她摔坏腿前的那个女友,对的,完美世界里他们要结婚了。所谓情场得意,事业失意,到了公司就因为没有老老实实在悉尼参加会议被Fire了,据称他偷跑去从林冒险了,事实上就和原版故事一样,人家就没让他去,他自己在那里自哀自怨了一番自然更没心情去开什么会了。

然而主角总是好运缠身,在停车场遇到了自己公司的老总Hugo,对的,这个世界里Hugo也得到了Happy ending,看起来他身上所有的灾难都没有发生了。一番谈话后Hugo让Locke去自己的另一家公司上班。真是好人哪!而另一家公司的负责人是得了癌症的Rose,最后她把Locke安排到学校去教书了,到了教师休息室看到了因为没人换咖啡滤纸而喋喋不休的欧洲历史学老师Ben,看来The others和Ocean众真是扯不断啊。

相比之下岛上就紧张多了,在黑烟版Locke因为其不和作正打算要干掉Richard的时候,一个只有他自己能看到的小孩出现了,看起来黑烟也有所顾忌,留下一番狠话后就放Richard走了。之后黑烟去找Sawyer,令人意外的是Sawyer一眼就认出了他不是Locke,当然这不重要,之后黑烟说服他跟自己走,向其证明他们来到小岛不是偶然。在路上的时候,之前那个小孩再次出现,给黑烟留下了一句,你知道规矩,你不能杀他。神奇的是Sawyer也能看到他。之后他们一起爬下悬崖到了一个洞里,洞的深处写满了名字,包括了Jack Sawyer等人,黑烟顺手划掉了Locke的,看来所有被划掉的名字的主人都向死神报道去了。诧异之时黑烟说出了玄机,这些名字都是候选者,Jacob的侯选。而且可以确定Jacob一定在某个时候见过这些人,看起来他们都是偶然到了岛上,实际上都是Jacob推波助澜而来。

最后事情就明了了,或者说看起来明了了,据黑烟所说Sawyer就是下一任Jacob,而他有三个选择,静观其变,或者是成为下任Jacob守护小岛,又或者是干脆放手,离开小岛。看来第三种选择对Sawyer更有吸引力,而这据称也刚好是黑烟的最大目的,他俩将要一起离岛了。

2010年2月16日星期二

Claire归来-Lost Final Season E03

剧名:What Kate Does
比较简单的一集,主要目的是带出失踪了整整一季的Claire,主角应该算是Claire,当然少不了kate
 
洛杉矶,从Kate劫车开始。一番紧张的逃窜之后,出租车司机弃车跑路,Kate把Claire赶下了车,后来却从行李中发现她怀孕了。搞开手铐后觉得过意不去,回去找Claire,一番交谈之后,两人似乎成了朋友。两人一起去见领养Claire孩子的夫妇,结果丈夫已经死了,妻子放弃了领养。Claire一阵慌乱,宝宝似乎要提前出世了,Kate只好将她送往医院。无巧不成书,给Claire看病的居然是是第一季中带走Claire的那个The Others Nathan。看来小岛被炸,不但Ocean 815过上了好日子,岛上别的人也正常生活了。一次阵痛中,Kate抓住了Claire的手,而Claire也莫名其妙地把自己未出世的儿子喊做Aaron,看来不管怎么变,有的事始终还是不会变。稳定下来后,Nathan表示Claire可以选择现在就生下孩子或者再等等。一天中受到这么多变故,看起来Claire一时无法接受,选择了再等等。后来的谈话中,Kate建议Claire留下这个孩子。之后警察跑来问话,Claire为Kate打了个掩护,在Kate跑路前还把自己的信用卡送给了她,看来两人的关系是越来越好了。
 
岛上的生活就没这么简单了,Sawyer杀了一个The Other后逃走,Kate表示自己能找到他,于是两个The Other 和 Jin 还有Kate出发了,然而一切都是Kate的计划,打晕两个The Other后,Kate跑去找Sawyer,而Jin决定回到神庙。找到Sawyer后,Kate和Sawyer在湖边又缅怀了一次Juliet,Sawyer再一次自责,要是当初自己没有因为惧怕孤独把Juliet留下,那她也就不会死了,唉,Lost里的几个男主角性格怎么都这么成问题啊。神庙里,带头大哥把Sayid电击烙铁了一番送了回去,然后告诉Jack Sayid被感染了,并给了他一颗药丸让他劝Sayid服下去,并表示如果不是本人自愿的话是没有效果的(好牛的药,还和服药者的心情相关)。这么多事之后Jack表示他连自己都不相信了又怎么会相信带头大哥。问题谈不下去之后,Jack一口把药吞了下去(以身试药,牛),这回是带头大哥急了,一番急救后让他把药吐了出来,并坦白那是一颗毒药,原因是Sayid已经被感染了,最终结果是被黑暗主宰(怎么这么诡异,难道真的要变成玄幻片了)。Jack好奇他们怎么知道的,得到的回答是这已经发生过一次了,令人震惊的是上一次是发生在Claire身上,更令人震惊的是就在两个被Kate打翻的The Others意图杀死准备回神庙的Jin的死后,一阵机枪扫射,两个The Other倒下了,Jin回头望去,Claire抬着机枪现身了。从可爱孕妇手拿机枪扫射,这变化也太夸张了吧。
 
下一集:I can prove
John要向Sawyer证明他为什么会来到岛上
 

2010年2月10日星期三

困扰多年的病

困扰我多年的一个病终于搞明白了,闪辉性暗点,可惜没得治。

2010年2月8日星期一

最终季——Lost归来

Lost最终季,不再有闪前,不再有闪回。故事紧接前一季,Juliet重伤之余拼命引爆氢弹成功,小岛被炸沉到了太平洋。Ocean815就此摆脱了坠机的命运,成功降落到洛杉矶国际机场。

Happy ending?没那么好的事了,首先是Charlie因为大麻被捕,Jin因为携带巨额现金被海关拉去问话,然后是Kate打翻FBI,持枪劫车再度潜逃,巧的是正好劫到了Claire的出租车,值得一提的是Jack的钢笔被她所偷,而在劫车之前还得到了Sawyer的一点帮助,最后是Jack和John,两人遭遇机场经典事件——行李失踪,分别是一箱刀子和装着老爸尸体的棺材一具,难道是Jack的老爸爬出棺材,偷了刀子跑路?两人在申报处相遇,一翻交流之后分道扬镳,考虑到Jack建议John来找自己免费咨询脊柱问题,两人应该还有更多的交集。

故事难道就此变成Lost之洛杉矶现实版。可惜Lost永远都是Lost,没有了闪前闪回,平行世界闪亮登台。在另一个世界里,Jack等人在氢弹爆炸之后从70年代回到了现在,大家从天鹅站的废墟里找到了Juliet,和Sawyer一番决别之后闭上了眼睛,在埋了她之后才得到了她的遗言——It's works,Hugo听从死后的Jacob的指示把大家带往神庙救助重伤的Sayid,到达黑烟所在的地洞之后被一帮人打翻拖到了神庙,原来是久违的The others,还记得第一季被抓的两个小孩还有某些所谓在Jacob名单上的人吗?都在这活得好好的呢。在报上Jacob的大名后,抄着日语的带头大哥把Sayid沉在水里,可惜伤没治好,人先挂了。

然后是假John,和第二架飞机上的人一番你来我往,干掉几个人并绑走Richard之后,其真面目终于揭露,他就和Jacob在一起的那家伙,并且他就是黑烟,而其目的是"回去"。回去哪呢?我大胆猜测是回外星。至于黑烟是什么呢?大家继续等待吧。不过看起来可以用某种粉末围个他穿不破的结界。再次大胆猜测他要回地狱。

最后是The others听说Jacob已死之后如临大敌,马上来始备战起来。而就在Jack和The others起冲突时Sayid一脸困惑的坐了起来。

Lost永远是Lost,解决掉的密团总是没有留下的多。