【问题标题】:Using std::less with nullptr将 std::less 与 nullptr 一起使用
【发布时间】:2015-03-02 13:30:58
【问题描述】:

以下代码sn-p中的断言是否总是成立?

std::less<Object *> lessPtr;
Object * o = new Object();
assert(lessPtr (o, nullptr) == false);

【问题讨论】:

  • 这是一个旧答案,引用了标准的一句话,说 less 可能不会像您期望的那样表现指针:stackoverflow.com/a/1099080。我怀疑答案是标准并不能保证,但在实践中应该没问题。

标签: c++ c++11


【解决方案1】:

简介

这个问题真的归结为在一个操作数是nullptr 的指针类型上使用小于关系运算符是否会产生“预期”结果;遗憾的是,事实并非如此。

结果是未指定

注意:请注意std::less 保证总订单;这意味着即使在使用函数对象时结果是未指定,它也必须在每次调用时产生相同的未指定值。


国际标准 (N3337) 怎么说?

5.9p2 关系运算符 [expr.rel]

可以比较指向相同类型的对象或函数的指针(指针转换后),结果定义如下:

  • 如果相同类型的两个指针 pq 指向同一个对象或函数,或者都指向同一个数组末尾的一个后,或者都为空,则 p&lt;=qp&gt;=q 均产生truep&lt;qp&gt;q 均产生false

  • 如果两个相同类型的指针 pq 指向不同的对象,这些对象不是同一对象的成员或同一数组的元素或不同的函数,或者如果其中只有一个是null,p&lt;qp&gt;qp&lt;=qp&gt;=q 的结果未指定。

  • 如果两个指针指向同一个对象的非静态数据成员,或者指向此类成员的子对象或数组元素,则如果两个成员具有相同的访问权限,则指向后面声明的成员的指针会比较大控制(第 11 条)并提供他们的类不是联合。

  • 如果两个指针指向具有不同访问控制(第 11 条)的同一对象的非静态数据成员,则结果未指定。

  • 如果两个指针指向同一个联合对象的非静态数据成员,则它们比较相等(在转换为void* 后,如有必要)。如果两个指针指向同一个数组的元素或一个超出数组末尾的元素,则指向具有较高下标的对象的指针比较高。

  • 未指定其他指针比较。

20.8.5p8 比较 [comparision]

对于模板greaterlessgreater_equalless_equal,任何指针类型的特化产生一个总顺序,即使内置运算符&lt;&gt;、@987654348 @, &gt;= 不要。


那么,标准的真正含义是什么?

T * p = new T;
T * q = nullptr;


p &lt; q 的判决是什么?
由于pq 不指向同一个数组的不同元素(包括数组最后一个元素之后的元素),并且两者都不指向同一个对象的非静态数据成员;执行p &lt; q(和p &gt; q)时的结果是未指定

bool a = p < q;  // unspecified
bool b = p < q;  // unspecified

assert (a == b); // can fire


std::less 呢?
但是,当使用 std::less 时,我们可以保证总订单 - 这实际上意味着以下断言不能触发 (standard-20.8.5p8)。

std::less<T*> comp;

bool a = comp (p, q);  // unspecified
bool b = comp (p, q);  // unspecified

assert (a == b);       // can not fire

【讨论】:

  • N3936 (C++14) 比 N3337 增加了更强的保证
【解决方案2】:

不,空指针相对于任何非空指针的顺序是未指定的。

如果操作数“指向不是同一对象的成员或同一数组的元素或不同函数的不同对象,或者其中只有一个为空”,则未指定比较运算符的结果。

std::less 和朋友对此进行了扩展以指定总顺序,但不指定空指针在该顺序中出现的位置。因此可以保证null 将始终大于或小于任何给定的非空指针。但它没有指定小于或大于所有非空指针。

【讨论】:

    猜你喜欢
    • 2011-04-12
    • 1970-01-01
    • 2021-03-23
    • 2015-03-06
    • 1970-01-01
    • 2015-06-21
    • 2014-08-29
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多