lesson4-C++内存管理

简介: lesson4-C++内存管理

C/C++内存分布

我们先来看一段代码:

int globalVar = 1;
static int staticGlobalVar = 1;
void Test()
{
  static int staticVar = 1;
  int localVar = 1;
  int num1[10] = { 1, 2, 3, 4 };
  char char2[] = "abcd";
  const char* pChar3 = "abcd";
  int* ptr1 = (int*)malloc(sizeof(int) * 4);
  int* ptr2 = (int*)calloc(4, sizeof(int));
  int* ptr3 = (int*)realloc(ptr2, sizeof(int) * 4);
  free(ptr1);
  free(ptr3);
}

第一组问题:

选项: A.   B.   C.数据段(静态区)  D.代码段(常量区)  

问题:以下变量存储在哪里?

  • globalVar
  • staticGlobalVar
  • staticVar
  • localVar
  • num1

第二段代码:

void Test()
{
  char char2[] = "abcd";
  const char* pChar3 = "abcd";
  int* ptr1 = (int*)malloc(sizeof(int) * 4);
  int* ptr2 = (int*)calloc(4, sizeof(int));
  int* ptr3 = (int*)realloc(ptr2, sizeof(int) * 4);
  free(ptr1);
  free(ptr3);
}

第二组问题:

选项: A.   B.   C.数据段(静态区)  D.代码段(常量区)  

问题:以下变量存储在哪里?

  •   char2      *char2
  • pChar3      *pChar
  •      ptr1      *ptr1

第三组问题:

  •   sizeof(num1)
  •   sizeof(char2)        strlen(char2)
  • sizeof(pChar3)       strlen(pChar3)
  •      sizeof(ptr1)

C语言中动态内存管理方式

malloc/calloc/realloc/free

C++中动态内存管理

C语言内存管理方式在C++中可以继续使用,但有些地方就无能为力,而且使用起来比较麻烦,因 此C++又提出了自己的内存管理方式:通过newdelete操作符进行动态内存管理

new/delete操作内置类型

newdelete操作自定义类型

operator new与operator delete函数

首先我们要明白operator new和operator delete是函数,而new和delete是操作符,他们直接是有联系,但不是重载关系,只是祖师爷起名字这么起。

operator new函数里调用了malloc函数,也就是说其实可以将他看做是malloc函数的封装,但是不同的是,malloc函数申请空间失败后返回NULL,而operator new函数里实现了判断malloc申请空间失败就抛出异常。

operator delete函数里也就是调用了free函数,这个函数主要是为了和operator new函数对称匹配。

new和delete的实现原理

对内置类型来说

new操作符底层只调用operator new函数,因为内置类型不需要构造函数和析构函数,所以new也不会调用构造函数

delete操作符只调用operator delete函数,同理,他也不会调用析构函数。

对自定义类型来说

new操作符的底层原理是先调用operator new函数,然后调用构造函数

delete操作符底层原理是先调用析构函数,然后调用operator delete函数

class Stack
{
public:
  Stack(int capacity = 4)
    :_capacity(capacity)
    ,_top(0)
  {
    _a = new int[capacity];
    _top++;
    cout << "构造" << endl;
  }
  ~Stack()
  {
    delete[] _a;
    _a = nullptr;
    _top = _capacity = 0;
    cout << "析构" << endl;
  }
private:
  int* _a;
  int _top;
  int _capacity;
};
int main()
{
  Stack* st = new Stack;
    delete st;
  return 0;
}

我们可以查看一下汇编代码来理解。

int main()
{
  Stack* st2 = new Stack[3];
  delete[] st2;
  return 0;
}

实际上三个对象的空间是一次性全部申请好,然后每个对象都调用构造函数。

析构的时候我们明明没有给delete[]传大小,他是怎么知道要析构三次的呢?

我们调试看一下内存

operator new[]本质上还是调用operator new函数

operator delete[]里面调用的是operater delete

定位new表达式(placement-new)

定位new是在已申请的原始内存空间中掉用一个构造函数初始化一个对象。

这个我们现阶段用不上,毕竟直接创建对象自动调用进行初始化多好,总不能malloc自定义类型的对象,然后使用定位new吧,就像这样:

哪个更好一目了然,我们的定位new真正用途是在内存池那里才会展现。

常见面试题

7.1 malloc/free和new/delete的区别

相同点:

都需要在堆上申请空间,并且都需要手动释放。

不同点:

  • malloc和free是函数,而new和delete是操作符
  • malloc开辟空间需要计算大小,而new只需要加上类型,如果需要开辟空间,只需要在[]里指定大小即可。
  • malloc返回值为void*类型,使用时需要强制转换,而new不需要。
  • malloc开辟内存空间失败返回NULL,而new则是抛出异常。
  • malloc开辟的内存空间是原始的,不会初始化,也不能初始化,而new开辟的内存空间可以手动初始化,如果是自定义类型,还会自动去调用他的构造函数;而delete在释放内存空间时会先去调用自定义类型对象的析构函数,free不会。

7.2 内存泄漏

内存泄漏就是因为疏忽或者其他原因未能释放已经不再使用的内存空间,失去了对该断内存的控制,最终导致内存出现浪费。

长期运行的程序出现内存泄漏危害很大,最终会导致响应越来越慢,最终卡死。

目录
相关文章
|
2月前
|
存储 编译器 C语言
内存管理【C++】
内存管理【C++】
43 1
|
2月前
|
存储 编译器 C语言
【C++】C\C++内存管理
【C++】C\C++内存管理
【C++】C\C++内存管理
|
2月前
|
存储 Java C语言
【C++】C/C++内存管理
【C++】C/C++内存管理
|
1月前
|
C语言 C++
C++(二)内存管理
本文档详细介绍了C++中的内存管理机制,特别是`new`和`delete`关键字的使用方法。首先通过示例代码展示了如何使用`new`和`delete`进行单个变量和数组的内存分配与释放。接着讨论了内存申请失败时的处理方式,包括直接抛出异常、使用`try/catch`捕获异常、设置`set_new_handler`函数以及不抛出异常的处理方式。通过这些方法,可以有效避免内存泄漏和多重释放的问题。
|
2月前
|
存储 编译器 C语言
C++内存管理(区别C语言)深度对比
C++内存管理(区别C语言)深度对比
72 5
|
4月前
|
存储 编译器 C语言
【C++】学习笔记——内存管理
【C++】学习笔记——内存管理
48 15
|
3月前
|
存储 C语言 C++
【C/C++】动态内存管理( C++:new,delete)
C++的`new`和`delete`用于动态内存管理,分配和释放内存。`new`分配内存并调用构造函数,`delete`释放内存并调用析构函数。`new[]`和`delete[]`分别用于数组分配和释放。不正确匹配可能导致内存泄漏。内置类型分配时不初始化,自定义类型则调用构造/析构。`operator new`和`operator delete`是系统底层的内存管理函数,封装了`malloc`和`free`。定位`new`允许在已分配内存上构造对象,常用于内存池。智能指针等现代C++特性能进一步帮助管理内存。
|
3月前
|
存储 编译器 程序员
【C/C++】动态内存管理(C:malloc,realloc,calloc,free)
探索C++与C语言的动态内存管理:从malloc到new/delete,了解内存分布及栈、堆的区别。文章涵盖malloc、realloc、calloc与free在C中的使用,强调内存泄漏的风险。C++引入new和delete,支持对象构造与析构,还包括operator new和placement-new。深入分析内存管理机制,揭示C与C++在内存处理上的异同。别忘了,正确释放内存至关重要!
|
3月前
|
算法 Java C++
C++和Python在内存管理上的主要区别是什么?
【7月更文挑战第2天】C++和Python在内存管理上的主要区别是什么?
93 1
|
4月前
|
C++
C/C++内存管理(2):`new`和`delete`的实现原理
C/C++内存管理(2):`new`和`delete`的实现原理