Spec-Zone.ru › C++

std::ranges::generate_random

Определён в заголовочном файле <random>
Сигнатура вызова
template< class R, class G >
    requires ranges::output_range<R, std::invoke_result_t<G&>> &&
             std::uniform_random_bit_generator<std::remove_cvref_t<G>>
constexpr ranges::borrowed_iterator_t<R>
    generate_random( R&& r, G&& g );
(1) (начиная с C++26)
template< class G, std::output_iterator<std::invoke_result_t<G&>> O,
          std::sentinel_for<O> S >
    requires std::uniform_random_bit_generator<std::remove_cvref_t<G>>
constexpr O
    generate_random( O first, S last, G&& g );
(2) (начиная с C++26)
template< class R, class G, class D >
    requires ranges::output_range<R, std::invoke_result_t<D&, G&>> &&
             std::invocable<D&, G&> &&
             std::uniform_random_bit_generator<std::remove_cvref_t<G>> &&
             std::is_arithmetic_v<std::invoke_result_t<D&, G&>>
constexpr ranges::borrowed_iterator_t<R>
    generate_random( R&& r, G&& g, D&& d );
(3) (начиная с C++26)
template< class G, class D, std::output_iterator<std::invoke_result_t<D&, G&>> O,
          std::sentinel_for<O> S >
    requires std::invocable<D&, G&> &&
             std::uniform_random_bit_generator<std::remove_cvref_t<G>> &&
             std::is_arithmetic_v<std::invoke_result_t<D&, G&>>
constexpr O
    generate_random( O first, S last, G&& g, D&& d );
(4) (начиная с C++26)

Пытается генерировать случайные числа с помощью функции-члена generate_random генератора случайных чисел или распределения, которая, как ожидается, будет более эффективной. Если функция-член generate_random недоступна, выполняет генерацию поэлементно.

Пусть резервная операция означает вызов ranges::generate(std::forward<R>(r), std::ref(g)) или ranges::generate(std::forward<R>(r), [&d, &g] { return std::invoke(d, g); }) для (1) или (3) соответственно.

1) Вызывает g.generate_random(std::forward<R>(r)), если это выражение корректно.
В противном случае пусть I будет равно std::invoke_result_t<G&>. Если R моделирует sized_range, заполняет r значениями ranges::size(r) типа I, выполняя неопределённое число вызовов вида g() или g.generate_random(s), если такое выражение корректно для значения N и объекта s типа std::span<I, N>.
В противном случае выполняет резервную операцию.
3) Вызывает d.generate_random(std::forward<R>(r), g), если это выражение корректно.
В противном случае пусть I будет равно std::invoke_result_t<D&, G&>. Если R моделирует sized_range, заполняет r значениями ranges::size(r) типа I, выполняя неопределённое число вызовов вида std::invoke(d, g) или d.generate_random(s, g), если такое выражение корректно для значения N и объекта s типа std::span<I, N>.
В противном случае выполняет резервную операцию.
2,4) Эквивалентно (1,3) соответственно, где r получается из ranges::subrange<O, S>(std::move(first), last).

Если эффекты (1) или (3) не эквивалентны эффектам соответствующей резервной операции, поведение не определено.

Значение N может различаться при разных вызовах. Реализации могут выбирать меньшие значения для более коротких диапазонов.

Функциональные объекты, описанные на этой странице, являются функциональными объектами алгоритмов (неофициально известными как niebloids

  • При вызове любого из них нельзя указывать явный список аргументов шаблона.
  • Ни один из них не виден для поиска, зависящего от аргументов.
  • Если какой-либо из них найден при помощи обычного неквалифицированного поиска в качестве имени слева от оператора вызова функции, поиск, зависящий от аргументов, подавляется.

Параметры

first, last - пара итератора и сентинела, задающая диапазон элементов, в которые записываются случайные числа
r - range, в который записываются случайные числа
g - генератор равномерных случайных битов
d - объект распределения случайных чисел

Примечания

На момент стандартизации std::ranges::generate_random в стандартной библиотеке нет генератора случайных чисел или распределения, предоставляющего функцию-член generate_random.

std::ranges::generate_random может быть более эффективным при использовании с определённым пользователем генератором случайных чисел, который оборачивает нижележащий векторизованный API.

Макрос проверки наличия функциональности Значение Стандарт Функциональность
__cpp_lib_ranges_generate_random 202403L (C++26) std::ranges::generate_random

Пример

#include <algorithm>
#include <iomanip>
#include <iostream>
#include <random>

int main()
{
    std::default_random_engine eng;
    std::default_random_engine::result_type rs[16]{};
    std::ranges::generate_random(rs, eng);
    
    std::cout << std::left;
    for (int i{}; auto n : rs)
        std::cout << std::setw(11) << n << (++i % 4 ? ' ' : '\n');
}

Возможный вывод:

16807       282475249   1622650073  984943658 
1144108930  470211272   101027544   1457850878
1458777923  2007237709  823564440   1115438165
1784484492  74243042    114807987   1137522503

См. также

ranges::generate
(C++20)
сохраняет результат функции в диапазоне
(функциональный объект алгоритма)
uniform_random_bit_generator
(C++20)
задаёт требования к типу, чтобы он считался генератором равномерных случайных битов
(концепт)

© cppreference.com
Licensed under the Creative Commons Attribution-ShareAlike Unported License v3.0.
https://en.cppreference.com/cpp/algorithm/ranges/generate_random

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API