【发布时间】:2019-05-09 09:03:34
【问题描述】:
在查看一些代码时,我遇到了一个包含以下行的构造:
if (const auto& foo = std::get_if<MyType>(&bar)) // note the ampersand!
其中bar 是std::variant<MyType, OtherType>。这里的问题是 get_if may return a null pointer 我不明白为什么该语句有效。
考虑这个类似的 MCVE:
#include <iostream>
struct Foo { int a = 42; };
Foo* f() { return nullptr; }
int main() {
const auto& foo = f(); // Returns a nullptr that binds to Foo*& - UB?
//static_assert(std::is_same<decltype(foo), const Foo*&>::value); // -> Fails
//const Foo*& bar = f(); // -> Fails
if (foo) std::cout << foo->a << std::endl;
else std::cout << "nullpointer" << std::endl;
}
main() 的第一行工作正常,我希望bar 的类型为const Foo*&,但静态断言失败。不出所料,以下行也无法使用 cannot bind non-const lvalue reference of type 'const Foo*&' to an rvalue of type 'const Foo*' 编译。
main 的第一条语句发生了什么?这是 UB 还是该标准是否包含一些允许其合法的隐藏秘密? bar的类型是什么?
【问题讨论】:
-
指针值的可能空值无关紧要 - 指向
T的空指针与指向T的所有其他指针具有相同的类型。nullptr不是指针,而是可以隐式转换为任何类型的空指针的对象。它的类型是nullptr_t。 -
get_if不能返回nullptr(这是一个类类型的值nullptr_t)。它必须返回一个指针值,它可以是一个空指针。 -
感谢@M.M. 的留言。然后我假设该引用具有误导性,因为它明确说明了返回值:“指向存储在指向变量中的值的指针或 null 指针 错误。” ?无论如何,我似乎需要更新我对空指针的了解。
-
@andreee “空指针”是指针的可能值。
nullptr不是空指针(也不是指针);它是一个可以隐式转换为任何类型的空指针的表达式。 -
@M.M 我想我已经搞定了......我想我在路上搞混了几件事,但我想现在我就在那里。我已经阅读了标准和参考中的一些部分,现在对我来说似乎很清楚。非常感谢您的评论,我从来没有想过我一直对空指针有一个完全错误的想法!
标签: c++ pointers reference c++17 auto