• c++11 动态内存管理-未初始化存储


    定义于头文件 

    复制一个对象到以范围定义的未初始化内存区域

    std::uninitialized_fill

    template< class ForwardIt, class T >
    void uninitialized_fill( ForwardIt first, ForwardIt last, const T& value );

    (1)

    template< class ExecutionPolicy, class ForwardIt, class T >
    void uninitialized_fill( ExecutionPolicy&& policy, ForwardIt first, ForwardIt last, const T& value );

    (2)(C++17 起)

    1) 复制给定的 value 到以 [first, last) 定义的未初始化内存区域,如同用

    for (; first != last; ++first)
      ::new (static_cast(std::addressof(*first)))
          typename std::iterator_traits::value_type(x);

    若初始化期间抛异常,则以未指定顺序销毁已构造的对象。

    2) 同 (1) ,但按照 policy 执行。此重载仅若 std::is_execution_policy_v> 为 true 才参与重载决议。

    参数

    first, last-要初始化的元素的范围
    value-构造元素所用的值
    policy-所用的执行策略。细节见执行策略。
    类型要求
    - ForwardIt 必须满足遗留向前迭代器 (LegacyForwardIterator) 的要求。
    - 通过 ForwardIt 合法实例的自增、赋值、比较或间接均不可抛异常。

    返回值

    (无)

    复杂度

    firstlast 间的距离成线性

    异常

    拥有名为 ExecutionPolicy 的模板形参的重载按下列方式报告错误:

    • 若作为算法一部分调用的函数的执行抛出异常,且 ExecutionPolicy 为标准策略之一,则调用 std::terminate 。对于任何其他 ExecutionPolicy ,行为是实现定义的。
    • 若算法无法分配内存,则抛出 std::bad_alloc 。

    可能的实现

    1. template<class ForwardIt, class T>
    2. void uninitialized_fill(ForwardIt first, ForwardIt last, const T& value)
    3. {
    4. typedef typename std::iterator_traits<ForwardIt>::value_type Value;
    5. ForwardIt current = first;
    6. try {
    7. for (; current != last; ++current) {
    8. ::new (static_cast<void*>(std::addressof(*current))) Value(value);
    9. }
    10. } catch (...) {
    11. for (; first != current; ++first) {
    12. first->~Value();
    13. }
    14. throw;
    15. }
    16. }

    调用示例

    1. #include <iostream>
    2. #include <vector>
    3. struct Foo
    4. {
    5. int N;
    6. Foo() {}
    7. explicit Foo(int n): N(n)
    8. {
    9. std::cout << "Foo(n)" << std::endl;
    10. }
    11. Foo(const Foo & o)
    12. {
    13. std::cout << "Foo(const Foo & o)" << std::endl;
    14. this->N = o.N;
    15. }
    16. Foo & operator =(const Foo &o)
    17. {
    18. std::cout << "operator =" << std::endl;
    19. this->N = o.N;
    20. return *this;
    21. }
    22. };
    23. int main()
    24. {
    25. std::vector<Foo> Fvector(5);
    26. std::uninitialized_fill(Fvector.begin(), Fvector.end(), Foo(5));
    27. std::cout << "Fvector size: " << Fvector.size() << std::endl;
    28. for (const Foo & o : Fvector)
    29. {
    30. std::cout << "Foo: " << o.N << std::endl;
    31. }
    32. }

    输出

     

    复制一个对象到以起点和计数定义的未初始化内存区域

    std::uninitialized_fill_n

    template< class ForwardIt, class Size, class T >
    void uninitialized_fill_n( ForwardIt first, Size count, const T& value );

    (1)(C++11 前)

    template< class ForwardIt, class Size, class T >
    ForwardIt uninitialized_fill_n( ForwardIt first, Size count, const T& value );

    (C++11 起)

    template< class ExecutionPolicy, class ForwardIt, class Size, class T >
    ForwardIt uninitialized_fill_n( ExecutionPolicy&& policy, ForwardIt first, Size count, const T& value );

    (2)(C++17 起)

    1) 复制给定值 value 到始于 first 的未初始化内存区域的首 count 个元素,如同以

    for (; n--; ++first)
      ::new (static_cast(std::addressof(*first)))
         typename std::iterator_traits::value_type(x);

    若初始化期间抛异常,则以未指定顺序销毁已构造的对象。

    2) 同 (1) ,但按照 policy 执行。此重载仅若 std::is_execution_policy_v> 为 true 才参与重载决议。

    参数

    first-要初始化的元素范围起始
    count-要构造的元素数量
    value-构造元素所用的值
    类型要求
    - ForwardIt 必须满足遗留向前迭代器 (LegacyForwardIterator) 的要求。
    - 通过 ForwardIt 合法实例的自增、赋值、比较或间接均不可抛异常。

    返回值

    (无)

    (C++11 前)

    指向最后复制的元素后一位置元素的迭代器。

    (C++11 起)

    复杂度

    count 成线性。

    异常

    拥有名为 ExecutionPolicy 的模板形参的重载按下列方式报告错误:

    • 若作为算法一部分调用的函数的执行抛出异常,且 ExecutionPolicy 为标准策略之一,则调用 std::terminate 。对于任何其他 ExecutionPolicy ,行为是实现定义的。
    • 若算法无法分配内存,则抛出 std::bad_alloc 。

    可能的实现

    1. template< class ForwardIt, class Size, class T >
    2. ForwardIt uninitialized_fill_n(ForwardIt first, Size count, const T& value)
    3. {
    4. typedef typename std::iterator_traits<ForwardIt>::value_type Value;
    5. ForwardIt current = first;
    6. try {
    7. for (; count > 0; ++current, (void) --count) {
    8. ::new (static_cast<void*>(std::addressof(*current))) Value(value);
    9. }
    10. return current;
    11. } catch (...) {
    12. for (; first != current; ++first) {
    13. first->~Value();
    14. }
    15. throw;
    16. }
    17. }

     调用示例

    1. #include <iostream>
    2. #include <vector>
    3. struct Foo
    4. {
    5. int N;
    6. Foo() {}
    7. explicit Foo(int n): N(n)
    8. {
    9. std::cout << "Foo(n)" << std::endl;
    10. }
    11. Foo(const Foo & o)
    12. {
    13. std::cout << "Foo(const Foo & o)" << std::endl;
    14. this->N = o.N;
    15. }
    16. Foo & operator =(const Foo &o)
    17. {
    18. std::cout << "operator =" << std::endl;
    19. this->N = o.N;
    20. return *this;
    21. }
    22. };
    23. int main()
    24. {
    25. std::vector<Foo> Fvector(5);
    26. std::uninitialized_fill_n(Fvector.begin(), 3, Foo(5));
    27. std::cout << "Fvector size: " << Fvector.size() << std::endl;
    28. for (const Foo & o : Fvector)
    29. {
    30. std::cout << "Foo: " << o.N << std::endl;
    31. }
    32. }

    输出

     

  • 相关阅读:
    Open AI ChatGPT Prompt 学习之基础篇
    代码随想录训练营二刷第四十六天 | 完全背包 518. 零钱兑换 II 377. 组合总和 Ⅳ
    使用 Helm Cli 将 chart 推送到 Harbor
    https比http安全在哪
    一天获4奖!大势智慧荣获2023测绘科学技术奖一等奖、地理信息科技进步奖一等奖、测绘科技创新优秀单位、地理信息产业最具成长性企业
    【语音识别】高斯混合模型(GMM)说话人识别【含Matlab源码 574期】
    图像运算和图像增强六
    顶级AI工具大盘点!
    云网融合赋能智慧转型,“天翼云管 ”开启贴身云管家时代
    Android存储:轻松掌握MMKV
  • 原文地址:https://blog.csdn.net/qq_40788199/article/details/126803506