天天看点

浅谈C++中的内存管理

大家都知道变量的生存周期这个概念,可是有的时候变量生存周期已经结束,但是所分配的那块内存空间还是存在的。文章举了四个不同的例子,来说明这其中的原因。

  正文:

  事情是因为这样一小段程序而来的。

int main()

{

int i=10;

int *j=&i;

if(!0)

int l=20;

int *k=&l;

j=k;

k=0;

}

cout<<*j;

return 0;

  我们用debug的方式来一步一步的分析,在watch的窗口下输入里面所有的变量。

int i=10;  //i is 10 and &i is 0x0012ff7c

int *j=&i; //*j is 10 and &j is 0x0012ff7c

//显然可以看出此时两个变量指的是同一地址

int l=20; //l is 20 and &l is 0x0012ff74

  /*地址0x0012ff7c—0x0012ff75被占据。要说明的是,

这个数值很有可能因为电脑硬件的不同而不同。*/

  int *k=&l; //*k is 20 and &k is 0x0012ff74

  //变量k与l指向同一地址。

  j=k;  //j is 0x0012ff74 and *j is 20

  /*指针间的赋值,这个语句的意思是把k指向的地址负值给j。

此时这两个变量指向的是同一个地址,都是0x0012ff74,而那

块地址存放的是20,所以也就有*j是20的原因。*/

cout<<*j; //*j is 20 and j is 0x0012ff74

/*此时同时可以看到k的地址是0x00000000,说明k这个变量

已经被自动销毁,所以地址指零。但是j所指的并不是k,而

是k所指的那段地址0x0012ff74,而由于此时j的生存周期还

没有结束(j是在if意外定义的),所以j指向的这块地址并

  至此,我们分析完了程序的全过程的内存分配情况,最终结果是这样的。(图1)

浅谈C++中的内存管理
浅谈C++中的内存管理

现在大家应该对上面那个程序的执行过程有一个大概地了解了吧!不过这个还不是我们想要得到的结果,我们需要的是打印一个不确定的结果。有了以上的分析,我们开始新的程序,让他打印出我们想要的东西。

  对于上面的程序,我们需要改动的是令变量j指向一个地址被释放的位置。于是就有了下面的程序。

int * foo()

return &l;

j = foo();

  编译器很“聪明”,编译后会给出一个警告。原话是“returning address of local variable or temporary”,指向的是上面程序的第四行,也就是return &l;这条语句。那句英文的意思也不用我再多解释了,相信大家都能看得明白。

这里还要说一件事情,就是在第一个程序当中,无论是debug版本还是release版本。执行完那个if语句以后,系统都是不会真正的把l清除掉,l只是k的一个别名。上面的程序是这样写的,用了*j=&i这样一句负值语句,而别名在MSDN中的解释与引用是相同的,所以也可以这样理解,int i=10; int &j=i;与上面的相同。不要去想上面这些程序了,大家再看看下面这个。

void f1( int *& j)

void any_function_use_local_variables()

int a,b,c;

a=b=c=100;

f1(j);

any_function_use_local_variables();

  请大家自己编译、执行,看看结果是什么,然后结合上面的两个例子,想想是为什么。下面再给大家一个小例子,可能会有助于理解内存的概念。

  程序的过程是试图去增加i,使之超过最大的整数。有一种情况是这个值被“卷回来”变成一个负数,在我的机器上程序的打印结果是-2147483648,这个结果可能因为硬件的不同而不同。

int i=1;

while(0<i) i++;

cout<<i;

  结束。

专注于企业信息化,最近对股票数据分析较为感兴趣,可免费分享股票个股主力资金实时变化趋势分析工具,股票交流QQ群:457394862

本文转自沧海-重庆博客园博客,原文链接:http://www.cnblogs.com/omygod/archive/2006/11/08/554570.html,如需转载请自行联系原作者

继续阅读