堆,栈与内存管理 & 扩展补充:类模板,函数模板,及其他
1-->stack(栈)和heap(堆)的释义:
1.0 Stack是存在于某作用域(scope)的一块内存空间。
1.1 例如,调用函数时,函数本身即会形成一个stack用来放置它所接收的参数,以及返回地址。在函数本体内声明的任何变量,其所使用的内存块都取自函数形成的stack。
1.2 Heap是指由操作系统提供的一块全局内存空间,程序可动态分配,从其中获得若干区块。
class Demo {……}; …… { Demo c1(10,20); //Stack(栈)中产生,出了作用域自动释放
Demo* p = new Demo(30); //Heap(堆)中产生,要另外写delete手动的释放 }
1.3 在上述区块中,c1对象在Stack栈中产生,出了区块作用域,自动释放。
1.4 Demo(30)是临时对象,占用的空间是以new动态分配而得,要另外配套delete消除。
1.5 栈对象的生命周期,在作用域结束时,生命终结。这种作用域内的对象是,又称为:auto object,因为它会被“自动”清理。
1.6 静态对象的生命周期,在出了作用域后仍然存在,直到整个程序结束。用static修饰的对象,不会在作用域结束前调用析构函数,而是在程序结束前调用析构函数。
1.7 全局对象的生命周期,比main更早之前就存在了,它会直到程序结束。可以把全局对象,看成是一种static修饰的对象。它们的作用域是整个程序。
1.8 new与delete必须成对的写出,不然出现内存泄露(memory leak),看下面伪代码,当作用域结束,p所批的heap object仍然存在,但指针P的生命却结束了,作用域之外再也看不到p(也就没机会delete p),但指针指向的那段空间还在,这样就是内存泄露。
class Demo {……}; …… { Demo* p = new Demo(30); //忘记了delete } //指针p离开作用域消亡
2--> new: 先分配内存,再调用构造(ctor)
3--> delete: 先调用析构,再释放内存