当前位置:   article > 正文

C++如何申请动态内存_c++申请动态内存

c++申请动态内存
1. C++如何申请动态内存
        在C++中,你可以使用`new`和`delete`关键字来申请和释放动态内存。这对于创建非静态存储期的对象或数组非常有用。下面是一些基本的例子:
  1. **单个对象:**
  2. int* ptr = new int; // 申请一个整数的内存
  3. *ptr = 5; // 在分配的内存中存储值5
  4. delete ptr; // 释放内存
  5. **对象数组:**
  6. int* ptr = new int[10]; // 申请一个10个整数的数组
  7. for (int i = 0; i < 10; ++i) {
  8.     ptr[i] = i; // 初始化数组
  9. }
  10. delete[] ptr; // 释放数组内存

        在使用`new`关键字时,C++会自动调用对象的构造函数(如果有的话),并在使用`delete`时调用析构函数。对于数组,使用`new[]`和`delete[]`。

2. new[] 后 不用delete[]有什么影响

        在C++中,如果你使用 `new[]` 来分配一个动态数组,但是忘记使用对应的 `delete[]` 来释放内存,将会导致几个问题:

        1. 内存泄漏:最直接的后果是内存泄漏。分配的内存将不会被回收,这意味着它仍旧被程序占用,直到程序结束。对于长时间运行的程序或多次分配而忘记释放的情况,内存泄漏可能导致越来越多的内存被占用,最终可能耗尽可用内存,影响程序或其他程序的性能,甚至导致程序崩溃。

        2. 资源泄漏:如果数组中的对象是某种类型的资源,比如文件句柄或网络连接,那么这些资源也不会被正确地释放。这可能导致资源耗尽,使得程序不能打开新文件或新网络连接。

        3. 对象析构:如果数组中的对象有非平凡的析构函数,那么不使用 `delete[]` 也意味着这些析构函数将不会被调用。这可能导致对象相关的清理工作没有被执行,比如释放它们可能持有的动态内存。

        4. 未定义行为:如果你错误地使用 `delete` 而不是 `delete[]`,这将导致未定义行为,因为 `delete` 只会调用单个对象的析构函数,而不是数组中每个对象的析构函数。

3. delete[]原理

        在C++中,`delete[]` 用于释放由 `new[]` 分配的动态数组内存。这是 `new[]` 和 `delete[]` 配对使用的一部分,确保了动态分配的数组能够被正确地创建和销毁。`delete[]` 的原理涉及几个步骤:

        1. 调用析构函数:`delete[]` 首先为数组中的每个元素调用其析构函数,从最后一个元素开始,逆序至第一个元素。这一步很重要,因为析构函数负责执行任何必要的清理工作,例如释放对象可能拥有的资源。对于基础数据类型(如 `int`、`double` 等)这步可能什么也不做,因为它们没有自定义的析构函数。

        2. 释放内存:一旦所有元素的析构函数被调用后,`delete[]` 会释放整个数组占用的内存块。这个内存块是连续的,由 `new[]` 一次性分配。

        3. 内存归还操作系统:释放的内存会归还给C++运行时的内存分配器,内存分配器可能将内存立即归还给操作系统,或者保留以满足后续的内存分配请求。

        在底层,`delete[]` 实现可能会调用操作系统提供的API来进行内存管理。不同的编译器和标准库实现可能有不同的内存管理策略,但概念上的操作是一致的。

4. delet[]是如何知道自己需要调用多少次析构函数的

        在C++中,当你使用 `new[]` 分配一个动态数组时,编译器会在内部记录数组的大小(即元素的个数)。这个信息被存储在动态分配内存的某个位置,通常是数组开始前的几个字节。不同的编译器和运行时库可能会以不同的方式存储这个信息,但这对于程序员来说是透明的。

        当你使用 `delete[]` 来释放这个数组时,运行时库会查找并读取它之前存储的大小信息,以确定需要调用析构函数的次数。然后,它会按照逆序(从最后一个元素到第一个元素)为数组中的每个元素调用析构函数。

        这是一个自动的过程,保证了即使你没有显式地记录数组的大小,`delete[]` 也能正确地为所有元素调用析构函数并释放整个数组的内存。

        这种机制也是为什么不能将 `new[]` 分配的内存用 `delete` 释放,或者将 `new` 分配的内存用 `delete[]` 释放的原因之一。这两者之间的内存管理和构造/析构的行为是不同的,`new` 和 `delete` 配对用于单个对象,而 `new[]` 和 `delete[]` 配对用于对象数组。混淆使用会造成未定义行为,很可能会导致程序崩溃。      

5. 如何避免使用错误

          为了避免这些复杂性,建议使用 C++11 之后引入的智能指针,如 `std::unique_ptr` 或 `std::shared_ptr`,特别是它们提供的特殊版本,可以与动态数组一起使用,并且可以自动处理内存释放的问题。例如:

  1. #include <memory>
  2. // 使用智能指针管理动态数组
  3. std::unique_ptr<int[]> smartArray(new int[10]);
  4. // 不需要手动调用 delete[],内存会在 smartArray 离开作用域时自动释放
声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/你好赵伟/article/detail/641084
推荐阅读
相关标签
  

闽ICP备14008679号