c++内存的分区

来源:互联网 发布:西科软件 知乎 编辑:程序博客网 时间:2024/06/05 00:49

有道云地址

C/C++的内存分区

1. 堆区

堆区存放的是动态申请的内存,以new,或则malloc申请的内存。

2. 栈区

栈区顾名思义是一个栈,它将程序的变量压入,退出作用域时弹出。

3. 静态/全局区

存储全局变量和函数的区域,一旦程序启动,就不再增减。

4. 常量区

存放常量的区域。

5 代码区

存放函数执行代码的区域

上代码

#include<iostream>#include<stdio.h>#include<stdlib.h>#include<string>using namespace std;static int a=0;const int  b=1;int c=2;static const int d=3;#define byte unsigned charvoid function(){    cout<<endl;}static void function1(){    cout<<endl;}class CA{public:    CA(){    }    void functionCA(){    }    static void functionst(){    }    virtual void functionv(){        cout<<endl;    }};int main(){    CA ca;    CA * ca1=new CA;    static int e=10;    const int f=11;    int g=12;    static const int h=13;    const static int h1=13;    const byte *pa=(byte*)malloc(96*sizeof(byte));    union {        void *pv;        void(CA::*pfn)();    } u;    u.pfn = &CA::functionCA;    byte *pb=new byte[96];    cout<<"malloc指针:"<<(int*)pa<<endl;    cout<<"new指针:"<<(int*)pb<<endl;    cout<<"对象地址:"<<&ca<<endl;    cout<<"new对象地址:"<<ca1<<endl;    cout<<"对象函数地址:"<<hex<<(int*)(long)u.pv<<endl;    cout<<"对象静态函数地址:"<<hex<<(int*)(long)&(CA::functionst)<<endl;    //u.pfn = &CA::functionv;    cout<<"对象虚函数函数地址:"<<((int*)*((int*)&ca+0))<<endl;    cout<<"对象虚函数函数地址:"<<((int*)*((int*)&ca+1))<<endl;    //cout<<(int*)&123<<endl;    cout<<"静态全局变量:"<<&a<<endl;    cout<<"全局常量:"<<&b<<endl;    cout<<"全局变量:"<<&c<<endl;    cout<<"静态全局常量:"<<&d<<endl;    cout<<"静态局部变量:"<<&e<<endl;    cout<<"局部常量:"<<&f<<endl;    cout<<"局部变量:"<<&g<<endl;    cout<<"静态局部常量:"<<&h<<endl;    cout<<"局部静态常量:"<<&h1<<endl;    cout<<"全局函数地址:"<<hex<<(int*)&function<<endl;    cout<<"全局静态函数地址:"<<hex<<(int*)&function<<endl;    string str="12345asd";    cout<<"字符串地址:"<<&str<<endl;    cout<<"字符串常量地址:"<<&"12345asd"<<endl;    delete[]pa,pb;    pa=0,pb=0;    delete ca1;    ca1=0;    return 0;}
结果malloc指针:0x91bc40new指针:0x91bcb0对象地址:0x7fff056aede0new对象地址:0x91bc20对象函数地址:0x402418对象静态函数地址:0x402423对象虚函数函数地址:0x402800对象虚函数函数地址:0静态全局变量:0x6042f0全局常量:0x402650全局变量:0x604118静态全局常量:0x402654静态局部变量:0x60411c局部常量:0x7fff056aedd8局部变量:0x7fff056aeddc静态局部常量:0x4027e8局部静态常量:0x4027ec全局函数地址:0x401d34全局静态函数地址:0x401d34字符串地址:0x7fff056aee10字符串常量地址:0x4027b5
  1. 凡是在编译时不能确定大小的区域,都在堆区,如动态分配的内存块等。

  2. 凡是全局的变量和局部的静态变量,即虽然在编译的时候可以确定大小,但是在程序运行时还保留有修改权限的量,都在静态/全局区

  3. 凡是全局的,一旦编译完毕就不改变(大小和内容)的,(即在整个程序的生存周期都存在的),都在常量区。 比如全局常量,全局函数,静态类函数,全局静态函数等,已经实例化的虚函数也在常数区。

  4. 凡作用区域不是整个函数周期的非静态量都在栈区。 局部变量和局部非静态常量都在栈区,局部的静态常量在常数区,非new的类对象等。

  5. 从上面的地址数据来看,常数区和函数区在一个地址,可以说函数区存放了常量,或则常量区存放了函数

额外知识点

  1. 取得类成员函数的地址
union {    void *pv;    void(CA::*pfn)();} u;u.pfn = &CA::functionCA;cout<<u.pv<<endl;
  1. 取得虚函数的地址,利用虚函数表的函数序号,函数序号对应的地址就是虚函数的地址,虚函数表在对象的开头
CA ca;  cout<<"对象虚函数函数地址:"<<((int*)*(int*)(&ca))<<endl;
0 0
原创粉丝点击