C++ 为什么允许从对象到引用的隐式转换?
让我们举个例子:C++ 为什么允许从对象到引用的隐式转换?,c++,casting,reference,type-conversion,C++,Casting,Reference,Type Conversion,让我们举个例子: Foo& Foo::operator+=(Foo val) { // logic... return *this; } Foo operator+(Foo v1, Foo v2) { return v1+=v2; } 如果表达式v1+=v2属于Foo&类型,为什么它可以用作返回Foo的函数的返回值?演员在哪里表演?一个操作符+=被实现为Foo的成员的事实有什么不同吗?C++允许您使用引用来代替对象。在对象按值返回(即通过复制)的情况下,编译器
Foo& Foo::operator+=(Foo val)
{
// logic...
return *this;
}
Foo operator+(Foo v1, Foo v2)
{
return v1+=v2;
}
如果表达式
v1+=v2
属于Foo&
类型,为什么它可以用作返回Foo
的函数的返回值?演员在哪里表演?一个操作符+=
被实现为Foo
的成员的事实有什么不同吗?C++允许您使用引用来代替对象。在对象按值返回(即通过复制)的情况下,编译器无论如何都要返回一个新对象;它只是将您返回的引用中的值分配给该对象,即
Foo operator+(Foo v1, Foo v2) {
Foo ret(v1+=v2); // << This is done implicitly
return ret;
}
Foo操作符+(Foo v1,Foo v2){
Foo-ret(v1+=v2);//引用不存在,它们只是对象的别名。两个重载运算符都应该将const
引用作为参数,而不是按值获取它们的参数,除非您喜欢通过到处复制对象的无用副本来燃烧无助的电子。这意味着+
运算符需要创建一个显式副本,但这对于在其他地方保存更多痛苦的电子来说是一个小代价。在本例中,我不能将v1
作为参考,因为我想使用+=
操作符来修改它,但不想修改原始对象。@Nightcat然后您可以创建一个本地副本,在其上使用+=
,然后返回It、 这样做的一个原因是,如果返回的对象是函数参数,则返回值优化不适用。但按值获取两个参数中的一个并像您所做的那样返回它并不少见。您所说的是隐式转换。没有隐式转换。转换是您需要的它在源代码中告诉编译器进行转换。强制转换总是显式的。这是否意味着v1
参数被复制了两次,第一次是通过函数调用,第二次是通过隐式构造函数调用?@Nightcat对,就是这样。当然,你完全可以控制复制的内容(例如,如果您想避免复制,可以标记itemsconst-Foo&v2
),因此编译器将此复制视为故意复制。