简体   繁体   English

使用 nullptr 作为 std::unordered_map 的键有什么后果吗?

[英]Are there any consequences in using a nullptr as a key for std::unordered_map?

Are there any side effects / problems that could arise in doing someMap.insert(make_pair(nullptr, nullptr)) ?在执行someMap.insert(make_pair(nullptr, nullptr))是否有任何副作用/问题? Not including the dangers of dereferencing the null pointer.不包括取消引用空指针的危险。

There is no violations in someMap.insert(make_pair(nullptr, nullptr)) . someMap.insert(make_pair(nullptr, nullptr))没有违规 But you need to pay attention when use this element to not dereference the nullptr or your program will have undefined behaviour (and may trigger a Segmentation Fault).但是你需要注意在使用这个元素时不要取消nullptr引用,否则你的程序会有未定义的行为(并且可能会触发 Segmentation Fault)。

Note: Obviously the map need to have a pointer in the key and a pointer in the value, or the expression can cause a compile error or in the worst case an Undefined Behaviour.注意:显然映射需要在键中有一个指针,在值中有一个指针,否则表达式会导致编译错误,或者在最坏的情况下会导致未定义行为。

This is fine.这可以。

A null pointer is a valid value for a pointer to hold.空指针是要持有的指针的有效值。 You can do anything with it that you can do with any other valid pointer, (except dereference it).你可以用它做任何你可以用任何其他有效指针做的事情(除了取消引用它)。

Do make sure that you pointers are valid.请确保您的指针有效。 If they are not, merely evaluating them has undefined behaviour ( implementation-defined behaviour since C++17 ).如果不是,仅对它们求值就具有未定义的行为(自 C++17 以来实现定义的行为)。 But evaluating a null pointer is fine because it's not "invalid", just undereferencable.但是评估一个空指针很好,因为它不是“无效”,只是无法引用。

The validity of this is entirely dependent on what exactly someMap is.这的有效性完全取决于someMap到底是什么。

Let's assume someMap has a key-type which is an actual pointer (that is, not a pointer-like type, but a T* of some kind).让我们假设someMap有一个键类型,它是一个实际的指针(也就是说,不是类似指针的类型,而是某种类型的T* )。

Then the question becomes what the validity is of comparing two pointers if one of them is nullptr .那么问题就变成了比较两个指针如果其中一个是nullptr的有效性。 Which means asking... how does the map compare its key type?这意味着要问……地图如何比较其键类型?

std::map 's key comparison is configurable. std::map的键比较是可配置的。 By default, it uses std::less<Key> .默认情况下,它使用std::less<Key>

This is important because normal ordering comparison of pointers using < or whatever only imposes a partial ordering between pointer values .这很重要,因为使用<或其他任何东西的指针的正常排序比较只会在指针值之间强加偏序 Pointers within the same array can be compared, as well as pointers to subobjects within the same object (ordered by declaration, for standard-layout types).可以比较同一数组中的指针,以及指向同一对象中子对象的指针(按声明排序,对于标准布局类型)。 Therefore, order-comparisons between a null pointer and any pointer value other than another null pointer is not permitted.因此,空指针和除另一个空指针以外的任何指针值之间的顺序比较是不允许的。

Fortunately for you, std::less has a specialization for pointers which imposes a total order to all pointer values .对你来说幸运的是, std::less对指针进行了专门化,它对所有指针值强加了一个总顺序 by contrast defines a total order for all pointers.相比之下,定义了所有指针的总顺序。

However, if you have provided a different comparison type, one which is based on invoking < rather than std::less , then you cannot insert nullptr into such a map .但是,如果您提供了一种不同的比较类型,一种基于调用<而不是std::less比较类型,那么您不能将nullptr插入到这样的map

If the key-type is some kind of pointer-like type, one which does comparisons based on the value of the pointer, then again, it had better be using std::less instead of < , or you're in trouble.如果键类型是某种类似指针的类型,一种基于指针的值进行比较的类型,那么最好使用std::less而不是< ,否则您会遇到麻烦。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM