2

I noticed that std::flat_set and std::flat_map container adaptors provide some noexcept member functions, in particular there are the followings:

[[nodiscard]] bool empty() const noexcept;
size_type size() const noexcept;

However, all the other container adaptors provide the same member functions as non-noexcept:

[[nodiscard]] bool empty() const;
size_type size() const;

At first, I agreed with the standard for not introducing the noexcept specific in the member functions, because there is not actually guarantee that the corresponding container's member functions are also noexcept. A possible solution could be introducing a conditionally noexcept, such as in many std::swap specializations.

So, I do not understand why the same member functions are declared noexcept in std::flat_set and std::flat_map.

Nicol Bolas
  • 449,505
  • 63
  • 781
  • 982
LoS
  • 448
  • 1
  • 3
  • 15
  • @273K containter adapters (`stack`, and `queue` don't have `noexcept` or `constexpr` attributes, at least according to cppreference). But `flat_map` and `flat_set` are not container adapters. – ALX23z Mar 24 '23 at 20:43
  • 3
    A lot of the other container adapters existed before C++11 and the introduction of `noexcept`. Most likely no one has made a proposal to add `noexcept` to them. – NathanOliver Mar 24 '23 at 20:47
  • 1
    @ALX23z, _24.6 Container adaptors , , _ It is written in the proposal of `std::flat_map`. – LoS Mar 24 '23 at 20:56
  • @Los `stack` and `queue` simply use basic functionality of the container and push/remove elements with different named functions. `flat_set` and `flap_map` have a lot more requirements for the underlying containters to function. – ALX23z Mar 24 '23 at 21:48
  • 1
    @273K `flat_map/set`'s containers can be provided by the user. – ALX23z Mar 24 '23 at 21:49
  • 1
    @273K, _A flat_set is a container adaptor that provides an associative container interface that supports unique keys_ It is written in original proposal. Both `std::flat_set` and `std::flat_map` proposals essentially describe them as container adaptors. They are very different from `std::stack` or `std::queue`, but this does not change the fact they are container adaptors. – LoS Mar 24 '23 at 22:04
  • You are looking for an opinion based answer. You can make a proposal to C++ committee. – 273K Mar 24 '23 at 22:42
  • @273K, the standard describes them as container adapters. Also in Stack Overflow there was an accepted answer to the question: https://stackoverflow.com/questions/74416249/is-flat-map-an-stl-container – LoS Mar 24 '23 at 22:56
  • This appears to be a defect in the standard. – 康桓瑋 Mar 25 '23 at 17:33

1 Answers1

0

After some researches, I found that adding the noexcept specific to a function can be dangerous. In fact, even though the function is simple, marking it noexcept might break existing code. This problem occurs precisely with the std::stack, std::queue, and std::priority_queue container adapters, that provide the empty() and size() member functions since C++98 and thus did not force implementers to use underlying container's member functions that are also noexcept. If the noexcept specific were introduced to such member functions, existing code might break.

A possible solution may be the use of a conditionally noexcept, that checks if the underlying container also use a noexcept function.

On the other hand, there are not problems for the std::flat_set and std::flat_map container adapters, because they were introduced after C++11 and therefore implementers are forced to use underlying container's member functions that are also noexcept.

LoS
  • 448
  • 1
  • 3
  • 15
  • For both `flat_set`/`flat_map` and `stack`/`queue`/`priority_queue`, `empty()` and `size()` just call the underlying container's function. They're... the same. It doesn't make sense to argue that one is okay but the other is not. – Barry Mar 27 '23 at 14:37
  • @Barry, they are the same, but when the std::stack, std::queue, and std::priority_queue container adapters were introduced in C++98, the underlying container did not have noexcept member functions. If the standard marked the member functions as noexcept, it is possible old custom containers continues to have non-noexcept empty() and size(), and this is a problem. – LoS Mar 28 '23 at 09:12