3422. Issues of seed_seq's constructors

Section: 29.5.8.1 [rand.util.seedseq] Status: C++23 Submitter: Jiang An Opened: 2020-03-25 Last modified: 2023-11-22

Priority: 3

View all other issues in [rand.util.seedseq].

View all issues with C++23 status.

Discussion:

29.5.8.1 [rand.util.seedseq] says that std::seed_seq has following 3 constructors:

  1. #1: seed_seq()

  2. #2: template<class T> seed_seq(initializer_list<T> il)

  3. #3: template<class InputIterator> seed_seq(InputIterator begin, InputIterator end)

The default constructor (#1) has no precondition and does not throw, and vector<result_type>'s default constructor is already noexcept since C++17, so #1 should also be noexcept.

Despite that the vector<result_type> member is exposition-only, current implementations (at least libc++, libstdc++ and MSVC STL) all hold it as the only data member of seed_seq, even with different names. And #1 is already noexcept in libc++ and libstdc++.

These constructors are not constrained, so #3 would never be matched in list-initialization. Consider following code:

#include <random>
#include <vector>

int main()
{
  std::vector<int> v(32);
  std::seed_seq{std::begin(v), std::end(v)}; // error: #2 matched and T is not an integer type
  std::seed_seq(std::begin(v), std::end(v)); // OK
}

#3 should be made available in list-initialization by changing Mandates in 29.5.8.1 [rand.util.seedseq]/3 to Constraints IMO.

[2020-04-18 Issue Prioritization]

Priority to 3 after reflector discussion.

[2021-06-23; Reflector poll]

Set status to Tentatively Ready after five votes in favour during reflector poll.

[2021-10-14 Approved at October 2021 virtual plenary. Status changed: Voting → WP.]

Proposed resolution:

This wording is relative to N4861.

  1. Modify 29.5.8.1 [rand.util.seedseq] as indicated:

    class seed_seq {
    public:
      // types
      using result_type = uint_least32_t;
    
      // constructors
      seed_seq() noexcept;
      […]
    };
    
    seed_seq() noexcept;
    

    -1- Postconditions: v.empty() is true.

    -2- Throws: Nothing.

    template<class T>
      seed_seq(initializer_list<T> il);
    

    -3- ConstraintsMandates: T is an integer type.

    -4- Effects: Same as seed_seq(il.begin(), il.end()).