【问题标题】:NULL vs nullptr (Why was it replaced?) [duplicate]NULL vs nullptr(为什么被替换?)[重复]
【发布时间】:2013-12-28 20:54:11
【问题描述】:

我知道在 C++ 中 0xNULL 在基于指针的应用程序中被 nullptr 取代。我只是好奇他们做出这个替换的确切原因?

在什么情况下使用nullptr而不是NULL在处理指针时有好处?

【问题讨论】:

  • @BryanChen 不是。我不想知道 nullptr 是什么...我想知道为什么要实施它以及如果您正确阅读了问题有什么好处
  • 阅读this answer
  • @BryanChen 中的几个关键字对我来说是不熟悉的,所以答案是不可读的......但是,不是重复的问题,只是同一主题中的一个问题,可能有用的答案跨度>
  • 也许this answer更容易理解

标签: c++ pointers null nullptr


【解决方案1】:

nullptr 的类型为 std::nullptr_t。它可以隐式转换为任何指针类型。因此,它将匹配 std::nullptr_t 或重载解析中的指针类型,但不匹配 int 等其他类型。

0(又名。C 的 NULL 桥接到 C++)可能会导致重载函数解析中的歧义,除其他外:

f(int);
f(foo *);

(感谢 Caleth 在 cmets 中指出这一点。)

【讨论】:

  • @Cheersandhth.-Alf 我不知道如何回答这个问题,除了我知道我在问什么,这是最容易理解的解释。
  • @Riptyde4:Shafik 的回答是恕我直言,是最全面的。那里的引用包括这个答案的“模棱两可的重载”和我的答案的“模板化参数类型问题”,而且它是一个很好的参考。这个答案只是一小部分原因。
  • 但是我们总是可以使用类型转换运算符来指定类型,例如 f( (int) NULL ) 或 f((foo*) NULL ) 作为解决歧义的替代方法...正确吗?
  • FWIW,我同意 Shafik 的回答更全面。事实上,我前段时间投了赞成票。
  • 吹毛求疵:nullptr的类型是std::nullptr_t,不是指针类型。 nullptr 隐式转换为任何指针类型,重要的是转换为任何整数类型。
【解决方案2】:

您可以通过阅读A name for the null pointer: nullptr 来很好地解释为什么它被替换,引用该论文:

这个问题分为以下几类:

  • 改进对库构建的支持,为用户提供一种编写不那么含糊的代码的方法,这样库编写者就不必担心整数和指针类型的重载。

  • 改进对泛型编程的支持,使整数 0 和 nullptr 更容易明确地表达。

  • 让 C++ 更易于教授和学习。

【讨论】:

    【解决方案3】:

    这里是Bjarne Stroustrup's wordings,

    在C++中,NULL的定义是0,所以只是审美上的区别。我更喜欢避免使用宏,所以我使用 0。NULL 的另一个问题是人们有时会错误地认为它不同于 0 和/或不是整数。在准标准代码中,NULL 有时被/被定义为不合适的东西,因此必须/必须避免。现在这种情况不太常见了。

    如果必须给空指针命名,就叫它nullptr;就是这样 它在 C++11 中调用。然后,“nullptr”将成为关键字。

    【讨论】:

    • 这并没有真正回答问题,只是给出了名称的来源......
    • @Quirliom:我认为这就是 C++11 中新关键字 nullptr 的原因
    【解决方案4】:

    一个原因:文字 0 倾向于获取类型 int,例如在完美的参数转发中或更一般地作为具有模板类型的参数。

    另一个原因:代码的可读性和清晰度。

    【讨论】:

    • 我同意但是:起源问题是关于 NULL 和 nullptr 的区别 ;-)
    • @hrfmobile: NULL 是一个宏,可以并且通常被定义为文字0(可能带有类型后缀)。在当前的 g++ 9.2 版中,它被定义为内在的__null。在当前的 Visual C++ 2019 中,它被定义为普通的 0。因此,我给出的第一个原因适用于 when NULL 被定义为文字。第二个原因总是适用的,但更主观。然而,大多数人都同意全大写是碍眼的,大喊大叫。这是宏使用该命名约定的主要原因。
    • 好吧,对于NULL的类型,C++标准可以添加std::nullptr_t而不添加nullptr,并定义#define NULL ((std::nullptr_t) 0),类似于POSIX在C中所做的:#define NULL ((void *) 0) .您不需要新的关键字。
    猜你喜欢
    • 2015-11-24
    • 1970-01-01
    • 2023-03-24
    • 2012-10-17
    • 2016-10-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-01-21
    相关资源
    最近更新 更多