1*732cb123SKonstantin Varlamov //===----------------------------------------------------------------------===//
2*732cb123SKonstantin Varlamov //
3*732cb123SKonstantin Varlamov // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4*732cb123SKonstantin Varlamov // See https://llvm.org/LICENSE.txt for license information.
5*732cb123SKonstantin Varlamov // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6*732cb123SKonstantin Varlamov //
7*732cb123SKonstantin Varlamov //===----------------------------------------------------------------------===//
8*732cb123SKonstantin Varlamov 
9*732cb123SKonstantin Varlamov #ifndef _LIBCPP___ALGORITHM_RANGES_SAMPLE_H
10*732cb123SKonstantin Varlamov #define _LIBCPP___ALGORITHM_RANGES_SAMPLE_H
11*732cb123SKonstantin Varlamov 
12*732cb123SKonstantin Varlamov #include <__algorithm/iterator_operations.h>
13*732cb123SKonstantin Varlamov #include <__algorithm/sample.h>
14*732cb123SKonstantin Varlamov #include <__algorithm/uniform_random_bit_generator_adaptor.h>
15*732cb123SKonstantin Varlamov #include <__config>
16*732cb123SKonstantin Varlamov #include <__iterator/concepts.h>
17*732cb123SKonstantin Varlamov #include <__iterator/incrementable_traits.h>
18*732cb123SKonstantin Varlamov #include <__iterator/iterator_traits.h>
19*732cb123SKonstantin Varlamov #include <__random/uniform_random_bit_generator.h>
20*732cb123SKonstantin Varlamov #include <__ranges/access.h>
21*732cb123SKonstantin Varlamov #include <__ranges/concepts.h>
22*732cb123SKonstantin Varlamov #include <__utility/forward.h>
23*732cb123SKonstantin Varlamov #include <__utility/move.h>
24*732cb123SKonstantin Varlamov #include <type_traits>
25*732cb123SKonstantin Varlamov 
26*732cb123SKonstantin Varlamov #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
27*732cb123SKonstantin Varlamov #  pragma GCC system_header
28*732cb123SKonstantin Varlamov #endif
29*732cb123SKonstantin Varlamov 
30*732cb123SKonstantin Varlamov #if _LIBCPP_STD_VER > 17 && !defined(_LIBCPP_HAS_NO_INCOMPLETE_RANGES)
31*732cb123SKonstantin Varlamov 
32*732cb123SKonstantin Varlamov _LIBCPP_BEGIN_NAMESPACE_STD
33*732cb123SKonstantin Varlamov 
34*732cb123SKonstantin Varlamov namespace ranges {
35*732cb123SKonstantin Varlamov namespace __sample {
36*732cb123SKonstantin Varlamov 
37*732cb123SKonstantin Varlamov struct __fn {
38*732cb123SKonstantin Varlamov 
39*732cb123SKonstantin Varlamov   template <input_iterator _Iter, sentinel_for<_Iter> _Sent, weakly_incrementable _OutIter, class _Gen>
40*732cb123SKonstantin Varlamov   requires (forward_iterator<_Iter> || random_access_iterator<_OutIter>) &&
41*732cb123SKonstantin Varlamov            indirectly_copyable<_Iter, _OutIter> &&
42*732cb123SKonstantin Varlamov            uniform_random_bit_generator<remove_reference_t<_Gen>>
43*732cb123SKonstantin Varlamov   _LIBCPP_HIDE_FROM_ABI
operator__fn44*732cb123SKonstantin Varlamov   _OutIter operator()(_Iter __first, _Sent __last,
45*732cb123SKonstantin Varlamov                       _OutIter __out_first, iter_difference_t<_Iter> __n, _Gen&& __gen) const {
46*732cb123SKonstantin Varlamov     _ClassicGenAdaptor<_Gen> __adapted_gen(__gen);
47*732cb123SKonstantin Varlamov     return std::__sample<_RangeAlgPolicy>(
48*732cb123SKonstantin Varlamov         std::move(__first), std::move(__last), std::move(__out_first), __n, __adapted_gen);
49*732cb123SKonstantin Varlamov   }
50*732cb123SKonstantin Varlamov 
51*732cb123SKonstantin Varlamov   template <input_range _Range, weakly_incrementable _OutIter, class _Gen>
52*732cb123SKonstantin Varlamov   requires (forward_range<_Range> || random_access_iterator<_OutIter>) &&
53*732cb123SKonstantin Varlamov            indirectly_copyable<iterator_t<_Range>, _OutIter> &&
54*732cb123SKonstantin Varlamov            uniform_random_bit_generator<remove_reference_t<_Gen>>
55*732cb123SKonstantin Varlamov   _LIBCPP_HIDE_FROM_ABI
operator__fn56*732cb123SKonstantin Varlamov   _OutIter operator()(_Range&& __range, _OutIter __out_first, range_difference_t<_Range> __n, _Gen&& __gen) const {
57*732cb123SKonstantin Varlamov     return (*this)(ranges::begin(__range), ranges::end(__range),
58*732cb123SKonstantin Varlamov                    std::move(__out_first), __n, std::forward<_Gen>(__gen));
59*732cb123SKonstantin Varlamov   }
60*732cb123SKonstantin Varlamov 
61*732cb123SKonstantin Varlamov };
62*732cb123SKonstantin Varlamov 
63*732cb123SKonstantin Varlamov } // namespace __sample
64*732cb123SKonstantin Varlamov 
65*732cb123SKonstantin Varlamov inline namespace __cpo {
66*732cb123SKonstantin Varlamov   inline constexpr auto sample = __sample::__fn{};
67*732cb123SKonstantin Varlamov } // namespace __cpo
68*732cb123SKonstantin Varlamov } // namespace ranges
69*732cb123SKonstantin Varlamov 
70*732cb123SKonstantin Varlamov _LIBCPP_END_NAMESPACE_STD
71*732cb123SKonstantin Varlamov 
72*732cb123SKonstantin Varlamov #endif // _LIBCPP_STD_VER > 17 && !defined(_LIBCPP_HAS_NO_INCOMPLETE_RANGES)
73*732cb123SKonstantin Varlamov 
74*732cb123SKonstantin Varlamov #endif // _LIBCPP___ALGORITHM_RANGES_SAMPLE_H
75