std::uninitialized_copy_n
<memory>
NoThrowForwardIt uninitialized_copy_n( InputIt first, Size count,
(constexpr since C++26)
class Size, class NoThrowForwardIt >
NoThrowForwardIt uninitialized_copy_n( ExecutionPolicy&& policy,
ForwardIt first, Size count,
for (; count > 0; ++d_first, (void) ++first, --count)
::new (voidify
(*d_first))
typename std::iterator_traits <NoThrowForwardIt>::value_type(*first);
std::is_execution_policy_v <std::decay_t <ExecutionPolicy>> is true.
(until C++20)std::is_execution_policy_v <std::remove_cvref_t <ExecutionPolicy>> is true.
(since C++20)
If d_first +
[
0,
count)
overlaps with first +
[
0,
count)
, the behavior is undefined.
Contents
[edit] Parameters
InputIt
must meet the requirements of LegacyInputIterator.
ForwardIt
must meet the requirements of LegacyForwardIterator.
NoThrowForwardIt
must meet the requirements of LegacyForwardIterator.
NoThrowForwardIt
may throw exceptions.
[edit] Return value
Iterator to the element past the last element copied.
[edit] Complexity
Linear in count.
[edit] Exceptions
The overload with a template parameter named ExecutionPolicy
reports errors as follows:
- If execution of a function invoked as part of the algorithm throws an exception and
ExecutionPolicy
is one of the standard policies, std::terminate is called. For any otherExecutionPolicy
, the behavior is implementation-defined. - If the algorithm fails to allocate memory, std::bad_alloc is thrown.
[edit] Notes
Feature-test macro | Value | Std | Feature |
---|---|---|---|
__cpp_lib_raw_memory_algorithms |
202411L |
(C++26) | constexpr for specialized memory algorithms, (1) |
[edit] Possible implementation
template<class InputIt, class Size, class NoThrowForwardIt> constexpr NoThrowForwardIt uninitialized_copy_n(InputIt first, Size count, NoThrowForwardIt d_first) { using T = typename std::iterator_traits <NoThrowForwardIt>::value_type; NoThrowForwardIt current = d_first; try { for (; count > 0; ++first, (void) ++current, --count) ::new (static_cast<void*>(std::addressof (*current))) T(*first); } catch (...) { for (; d_first != current; ++d_first) d_first->~T(); throw; } return current; }
[edit] Example
#include <algorithm> #include <iostream> #include <memory> #include <string> #include <tuple> #include <vector> int main() { std::vector <std::string > v = {"This", "is", "an", "example"}; std::string * p; std::size_t sz; std::tie (p, sz) = std::get_temporary_buffer <std::string >(v.size()); sz = std::min (sz, v.size()); std::uninitialized_copy_n(v.begin(), sz, p); for (std::string * i = p; i != p + sz; ++i) { std::cout << *i << ' '; i->~basic_string<char>(); } std::cout << '\n'; std::return_temporary_buffer (p); }
Possible output:
This is an example
[edit] Defect reports
The following behavior-changing defect reports were applied retroactively to previously published C++ standards.
DR | Applied to | Behavior as published | Correct behavior |
---|---|---|---|
LWG 2133 | C++98 | the effect description used a for loop with the iteration expression ++d_first, ++first, --count, which results in argument-dependent lookups of operator, |
discards the value of one operand to disable those ADLs |
LWG 2433 | C++11 | this algorithm might be hijacked by overloaded operator& | uses std::addressof |
LWG 3870 | C++20 | this algorithm might create objects on a const storage | kept disallowed |
[edit] See also
(algorithm function object)[edit]