标签:
T operator+(const T &, const T &);以及两个T objects,a和b,那么:
a + b;可能会导致一个临时性对象,以放置传回的对象.是否会导致一个临时性对象,视编译器的进取性(aggressiveness)以及上述操作发生时的程序上下关系(program context)而定.例如下面这个片段:
T a, b; T c = a + b;编译器会产生一个临时性对象,放置a+b的结果,然后再使用T的copy constructor,把该临时性对象当作c的初值.然而更好的转换则是直接以拷贝构造的方式,将a+b的值放到c中,于是就不需要临时性对象,以及对其constructor和destructor的调用了.
T c = a + b;而其中的加法运算符被定义为:
T operator+(const T &, const T &);或
T T::operator+(const T &);那么实现时根本不产生一个临时性对象.
c = a + b;不能够忽略临时性对象.
T c = a + b;总是比下面的操作更有效率地被编译器转换:
c = a + b;第三种运算形式是,没有出现目标对象:
a + b; // no target这时候有必要产生一个临时对象,以放置运算后的结果.虽然看起来有点怪异,但这种情况实际上在子表达式中十分普遍.例如,如果这样写:
String s("hello"), t("world"), u("!");那么不论:
String v;
v = s + t + u;或
printf("%s\n", s + t);都会产生一个临时对象,与s + t相关联.
// tertiary full expression with 5 sub-expressions ((objA > 1024) && (objB > 1024)) ? objA + objB : foo(objA, objB);一种有五个子表达式,内带在一个"?:完成表达式"中.任何一个子表达式所产生的任何一个临时对象,都应该在完整表达式被求值完成后,才可以销毁.
if (s + t || u + v)其中的u+v子算式只有在s+t被评估为 false 时,才会开始被评估.与第二个子算式有关的临时性对象必须被销毁.但是,很显然地,不可以被无条件地销毁.也就是说,希望只有在临时性对象被产生出来的情况下才去销毁它.(如果第一个子算式为 true,则不产生第二个临时性对象,不需要销毁)
bool verbose; ... String progNameVersion = !verbose ? 0 : progName + progVersion;其中progName和progVersion都是String objects.这时候会生出一个临时对象,放置加法运算符的运算结果:
String operator+(const String &, const String &);临时对象必须根据对verbose的测试结果有条件地解构.在临时对象的生命规则下,它应该在完整的"?:表达式"结束评估后尽快被销毁.然而,如果progNameVersion的初始化需要一个copy constructor:
progNameVersion.String::String(temp);那么临时性对象的解构(在"?:完整表达式"之后)当然那就不是期望的.C++ Standard要求:
const String &space = " ";产生出这样的程序代码:
// C++ pseudo Code String temp; temp.String::String(" "); const String &space = temp;很明显,如果临时性对象现在被销毁,那个reference也就没有用了.所以C++ Standard要求:
版权声明:本文为博主原创文章,未经博主允许不得转载。
标签:
原文地址:http://blog.csdn.net/yiranant/article/details/47733885