局部变量的堆栈问题

今天看堆栈有关的算法时突然又想到了局部变量的压栈问题,在局部函数里面先定义的变量先压栈,按照所所需的大小分配内存,先压栈的变量地址会大些,这个不知是否跟编译器的实现有关,问题来了

int n = 1;

int m  = 2;

int k = 3;

int *p = &k;

cout<<&n<<endl;
cout<<&m<<endl;
cout<<&k<<endl;
cout<<sizeof(int)<<endl;

for (int i = 0; i < 3;i++)
{
    cout<<*p<<endl;
    p+=3;
}

运行结果

我的64位机,发现在VS2008下编译时m,n,k地址变化是符合那个压栈规律的,运行后你会发现地址便不是相差sizeof(int),居然是12个字节。还以为自己只是记错了

于是赶紧在Linux下用G++编译

这个是正常的,vc6.0下也没问题

这个说明还是跟便以其有关,后面有时间详细总结下C/C++中的代码,变量,函数的区段和生存周期问题

时间: 2024-10-11 13:46:46

局部变量的堆栈问题的相关文章

局部变量与堆栈

    我们知道函数中的局部变量存储在堆栈之中,如下图所示,当局部变量1.2.3存到堆栈中后,堆栈指针ESP并没有下移,依然指向原来的位置.出现这种情况的原因是:局部变量进入堆栈并不是使用push而是使用mov操作,所以ESP无变化.正是因为这样,如果函数把任何数据压入堆栈,那么局部变量将会被覆盖.   为了保护局部变量,解决方法是在函数代码的开始添加一行(针对汇编语言),通过从ESP寄存器减去一个值,为局部变量保留一定数量的堆栈空间.如下图所示: 现在,如果把任何数据压入堆栈,数据会被存放在局

Java变量类型,实例变量 与局部变量 静态变量

实例变量: 实例变量在类中声明,但在方法的外面,构造函数或任何块. 当空间分配给某个对象在堆中,插槽为每个实例变量创建值. 当一个对象与使用关键字 “new” 来创建,在对象被销毁销毁创建的实例变量. 实例变量认为必须由一个以上的方法,构造函数或块,或一个对象的状态的关键部分必须出现在整个类中引用的值. 实例变量可以在使用前或后级的级别声明. 访问修饰符可以给出实例变量. 实例变量对于所有方法,构造函数和块在类中可见.通常,建议,使这些变量私有(接入层).然而能见度子类可以给这些变量与使用访问修

java堆、栈、堆栈的区别

1.栈(stack)与堆(heap)都是Java用来在Ram中存放数据的地方.与C++不同,Java自动管理栈和堆,程序员不能直接地设置栈或堆. 2. 栈的优势是,存取速度比堆要快,仅次于直接位于CPU中的寄存器.但缺点是,存在栈中的数据大小与生存期必须是确定的,缺乏灵活性.另外,栈数据可以共 享,详见第3点.堆的优势是可以动态地分配内存大小,生存期也不必事先告诉编译器,Java的垃圾收集器会自动收走这些不再使用的数据.但缺点是,由于要 在运行时动态分配内存,存取速度较慢. 3. Java中的数

Java中的堆和栈以及堆栈的区别

在正式内容开始之前要说明一点,我们经常所说的堆栈堆栈是堆和栈统称,堆是堆,栈是栈,合在一起统称堆栈: 1.栈(stack)与堆(heap)都是Java用来在Ram中存放数据的地方.与C++不同,Java自动管理栈和堆,程序员不能直接地设置栈或堆. 2. 栈的优势是,存取速度比堆要快,仅次于直接位于CPU中的寄存器.但缺点是,存在栈中的数据大小与生存期必须是确定的,缺乏灵活性.另外,栈数据可以共 享,详见第3点.堆的优势是可以动态地分配内存大小,生存期也不必事先告诉编译器,Java的垃圾收集器会自

流畅的python学习笔记第八章:深拷贝,浅拷贝,可变参数

首先来看赋值,浅拷贝,深拷贝. 一赋值: a=['word',2,3] b=a print id(a),id(b) print [id(x) for x in a] print [id(x) for x in b] a[0]='hello' print a print b E:\python2.7.11\python.exe E:/py_prj/fluent_python/chapter8.py 24709080 24709080 [24410496, 21298404, 21298392] [

华为C/C++笔试题&amp;答案

1.static有什么用途?(请至少说明两种) 1)在函数体,一个被声明为静态的变量在这一函数被调用过程中维持其值不变. 2) 在模块内(但在函数体外),一个被声明为静态的变量可以被模块内所用函数访问,但不能被模块外其它函数访问.它是一个本地的全局变量. 3) 在模块内,一个被声明为静态的函数只可被这一模块内的其它函数调用.那就是,这个函数被限制在声明它的模块的本地范围内使用 2.引用与指针有什么区别? 1) 引用必须被初始化,指针不必. 2) 引用初始化以后不能被改变,指针可以改变所指的对象.

C/C++ 经典面试题汇总

面试题1:变量的声明和定义有什么区别 ? 为变量分配地址和存储空间的称为定义,不分配地址的称为声明.一个变量可以在多个地方声明,但是只在一个地方定义.加入extern修饰的是变量的声明,说明此变量将在文件以外或在文件后面部分定义. 说明:很多时候一个变量,只是声明不分配内存空间,直到具体使用时才初始化,分配内存空间,如外部变量. 面试题2:写出bool .int. float.指针变量与"零值"比较的if语句 bool型数据: if(flag) { A; } else { B:} in

01-java学习笔记01

1.面向对象 面向对象:三个特征:封装, 继承, 多态 类和对象的关系 类就是:对现实生活中的事物的描述. 对象:就是这类事物,实实在在存在个体. 1 class Car 2 { 3 String color = "黄色"; 4 int num = 4; 5 6 void run() 7 { 8 System.out.println( color+ ".."+num ); 9 } 10 } 11 12 public class CarDemo 13 { 14 pub

C++概念

1.new.delete.malloc.free关系 delete会调用对象的析构函数,和new对应free只会释放内存,new调用构造函数.malloc与free是C++/C语言的标准库函数,new/delete是C++的运算符.它们都可用于申请动态内存和释放内存.对于非内部数据类型的对象而言,光用maloc/free无法满足动态对象的要求.对象在创建的同时要自动执行构造函数,对象在消亡之前要自动执行析构函数.由于malloc/free是库函数而不是运算符,不在编译器控制权限之内,不能够把执行