熟悉c++的朋友应该都知道,c++提供给了程序员与硬件打交道的可能性,比如说内存管理。一个高水平的c++程序员可以将c++程序的性能优化到极致,榨干硬件资源。而现在我想说说与内存管理有关的new 和 malloc()。

  先说说malloc(),malloc是从C语言那里继承过来的一个函数,其用于分配一片内存,它的返回结果是一个指向你所需求的内存的指针,其函数原型和使用例子如下:

/*  函数原型  其中__size是你要分配的大小,其单位是byte*/void* malloc(size_t __size);// 用例int* pInt = (int*) malloc(sizeof(int));               // 分配了一个intdouble* pDoubleArray = (double*) malloc(sizeof(double) * 5);   // 分配了一个double数组,其大小为5

  一般来说,malloc总是能为你分配出内存。但是也存在山穷水尽,内存不够用的情况。这时候malloc会返回一个空指针(NULL, nullptr)。当你使用malloc的时候,你最好每次都要判断一下返回的指针是否为空。

相关教程:C++视频教程

  现在内存已经分配出来了。当程序运行到某一些时刻,我又不想要这些内存了。这时候我们就要手动释放内存,否则的话就会造成内存泄露。通过free() 函数来释放内存,其函数原型和使用例子如下:

// 原型void free(void* __ptr);// 用例free(pInt);free(pDoubleArray);

  有趣的是你传给free函数的只是一个指针,然而不管你是分配了一个元素还是分配了一个数组,free总能帮你释放掉这些内存(free 怎么知道你分配的数组的大小?)

  让我来详细的说说malloc在分配内存的时候干了什么。malloc在分配内存的时候,不仅仅会分配你需要的内存大小,它还会在你的内存的头部和尾部加上一些额外的信息(俗称cookie)。比如说用来DEBUG的信息和你的内存的大小。这就解释了为什么能free掉你的内存,因为它知道你这块内存是多大的。值得一提的是这些Cookie会占用一些内存。。。

  好了,malloc已经介绍的差不多了。还想说的一点是malloc只是一个第三方的函数,并不是操作系统的内核函数。如果有额外的需求的话,你可以设计自己的malloc。接下来谈谈new。

  new是c++提供的一个操纵符(或者说关键字)。其也是用于分配内存的。其用例如下:

int* pInt = new int(3);            // 分配并构造一个intdouble* pDoubleArray = new double[5];    // 分配了一个double数组,其大小是5delete pInt;                   // 删除单元素delete[] pDoubleArray;             // 删除数组

  还是老话题,一般来说程序是能为你分配出内存的,但是实在山穷水尽了怎么办?这时候程序就会抛出一个std::bad_alloc异常。注意,这是new 和 malloc 的区别之一。但是难能可贵的是C++提供了一个机制来处理bad_alloc异常,其做法如下:

void BadAllocateHandler(){  std::cout << "啊,内存分配失败了" << std::endl;  exit(0);}std::set_new_handler(BadAllocateHandler);

  BadAllocateHandler是程序员自己写的当分配失败时的处理函数。而set_new_handler是c++提供的机制。一般来说当山穷水尽的时候你所应该做的事只有两件。要么让程序退出,要么想办法从别的地方挖一些内存来继续分配。

  你已经知道了new是一个关键字。对于一个程序来说,一切的动作都将回到函数调用。所以new的时候到底发生了什么呢?当你new的时候,首先程序会去调用::operator new()这个函数。然后::operator new()中程序会去调用malloc()。 喔!一切都明了了,原来new的本质也是去调用malloc函数!!同理,delete的本质是去调用free()函数。

  虽然new的本质是去调用malloc,但是new 和 malloc还有一点很大的不同。那就是new 出来内存后,new会帮你把对象给构造出来,而malloc只是分配内存。具体例子如下:

class MyObj {public:  public MyObj(int value) : val(value) {}  int val;};MyObj* obj = new MyObj(4);MyObj* obj1 = (MyObj*) malloc(sizeof(MyObj));

  new 的做法是在malloc分配出内存后,编译器会直接调用类的构造函数在这片内存中构造出对象。注意!只有编译器能直接调用类的构造函数。而你使用malloc的话,是无法直接在上面构造出对象的。

更多相关文章

  1. srand(time(null))函数是什么意思
  2. srand(time(0))函数是什么意思
  3. malloc函数的用法
  4. c语言定义函数
  5. memcpy函数用法
  6. c语言函数调用例子
  7. c++如何实现字符串分割函数split?(代码示例)
  8. c语言find函数的用法详解
  9. c++如何从函数返回数组

随机推荐

  1. 自学第五十二天
  2. 华为交换机开启Telnet服务及修改端口
  3. 【前端词典】Vuex 注入 Vue 生命周期的过
  4. 初次见面,请多关注
  5. 写独立个人博客,还有机会吗?
  6. 【前端词典】如何向老板解释反向代理
  7. 25条很棒的Python一行代码,建议收藏!
  8. Ansible 之 配置文件解析
  9. 【前端词典】学习 Vue 源码的必要知识储
  10. 搭建个人博客,我遇到哪些棘手的问题?