大括号初始化防止非常量使用临时
Brace initialization prevents non-const use of temporary
我想创建一个 const 对象的临时副本并以非常量方式使用它:
struct S {
S& f() { return *this; }
};
int main() {
const S a{};
S{a}.f(); // Error on this line
return 0;
}
使用 msvc(Visual Studio 2017,C++14),我得到这个错误:
Error C2662 'S &S::f(void)': cannot convert 'this' pointer from 'const S' to 'S &'
如果我将大括号初始化更改为经典初始化,它会起作用:
S{a}.f(); // Does not work
S(a).f(); // Works
两种变体都可以在 gcc 中正常编译。我是不是遗漏了什么或者这是一个编译器错误?
它看起来像是一个编译器错误,或者是一个奇怪的优化的结果,因为原始代码的这种变体只使 ctors 和 dtor 具有副作用,使用 MSVC 可以很好地编译:
#include <iostream>
struct S {
S(const S& other) {
std::cout << "Copy ctor " << &other << " -> " << this << std::endl;
}
S() {
std::cout << "Default ctor " << this << std::endl;
}
~S() {
std::cout << "Dtor " << this << std::endl;
}
S& f() { return *this; }
};
int main() {
const S a{};
std::cout << &a << std::endl;
S{a}.f();
return 0;
}
编译成功,输出为:
Default ctor 0306FF07
Copy ctor 0306FF07 -> 0306FF06
Dtor 0306FF06
Dtor 0306FF07
似乎是另一个 MSVC 错误。
S{a}
被推导为 const struct S
,这就是错误。
#include <string>
#include <iostream>
template < class T >
std::string type_name()
{
std::string p = __FUNCSIG__;
return p.substr( 106, p.length() - 106 - 7 );
}
struct S {
S& f() { return *this; }
};
int main() {
const S a{};
//S{a}.f(); // Error on this line
std::cout << type_name<decltype(S{a})>() << std::endl;
return 0;
}
输出:
const struct S
我想创建一个 const 对象的临时副本并以非常量方式使用它:
struct S {
S& f() { return *this; }
};
int main() {
const S a{};
S{a}.f(); // Error on this line
return 0;
}
使用 msvc(Visual Studio 2017,C++14),我得到这个错误:
Error C2662 'S &S::f(void)': cannot convert 'this' pointer from 'const S' to 'S &'
如果我将大括号初始化更改为经典初始化,它会起作用:
S{a}.f(); // Does not work
S(a).f(); // Works
两种变体都可以在 gcc 中正常编译。我是不是遗漏了什么或者这是一个编译器错误?
它看起来像是一个编译器错误,或者是一个奇怪的优化的结果,因为原始代码的这种变体只使 ctors 和 dtor 具有副作用,使用 MSVC 可以很好地编译:
#include <iostream>
struct S {
S(const S& other) {
std::cout << "Copy ctor " << &other << " -> " << this << std::endl;
}
S() {
std::cout << "Default ctor " << this << std::endl;
}
~S() {
std::cout << "Dtor " << this << std::endl;
}
S& f() { return *this; }
};
int main() {
const S a{};
std::cout << &a << std::endl;
S{a}.f();
return 0;
}
编译成功,输出为:
Default ctor 0306FF07
Copy ctor 0306FF07 -> 0306FF06
Dtor 0306FF06
Dtor 0306FF07
似乎是另一个 MSVC 错误。
S{a}
被推导为 const struct S
,这就是错误。
#include <string>
#include <iostream>
template < class T >
std::string type_name()
{
std::string p = __FUNCSIG__;
return p.substr( 106, p.length() - 106 - 7 );
}
struct S {
S& f() { return *this; }
};
int main() {
const S a{};
//S{a}.f(); // Error on this line
std::cout << type_name<decltype(S{a})>() << std::endl;
return 0;
}
输出:
const struct S