You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为何两次调用test()时类A对象的this地址相同?如何确保地址不同?

你的C++对象地址疑问:解析与解决方案

嘿,这个问题挺典型的!先给你捋清楚来龙去脉:

为什么两次输出的this地址相同?

你的推理逻辑本身没毛病——不同的对象实例确实应该拥有唯一的内存地址,但前提是它们的生命周期有重叠。而你的代码里,test()函数中的A a是栈上的局部变量:

  • 第一次调用test()时,程序在栈上为a分配一块内存,函数返回后,这块内存会被标记为"可用"(但不会立刻被清空或覆盖);
  • 第二次调用test()时,编译器/运行时发现栈顶刚好有一块大小合适的空闲内存,就直接复用了这块空间。

因为两个a对象的生命周期完全不重叠(一个销毁后另一个才创建),所以复用同一块内存是完全符合C++标准的优化行为,不算异常。

如何确保两个A类对象拥有不同地址?

如果你需要的是同时存在的两个对象地址不同,或者哪怕生命周期不重叠也想让它们用不同地址,可以试试这几种方法:

1. 使用堆内存分配

把局部变量改成堆上分配,每次new都会从堆中申请新的空闲内存(除非系统内存耗尽):

class A { 
public: 
    A(){ cout << this << endl; } 
}; 
void test() { 
    A* a = new A(); // 堆上分配
    // 记得用完后delete a; 或者用智能指针避免内存泄漏
} 
int main() { 
    for(int i = 0; i < 2; ++i) test(); 
    return 0; 
}

2. 让两个对象的生命周期重叠

如果两个对象同时存在于内存中,它们的地址必然不同。比如修改代码让两个对象在main函数中同时创建:

class A { 
public: 
    A(){ cout << this << endl; } 
}; 
void test(A& obj) { 
    // 这里操作传入的对象,不再创建新对象
} 
int main() { 
    A a1, a2; // 两个对象同时存在,地址不同
    test(a1);
    test(a2);
    return 0; 
}

或者用容器存储多个对象,确保它们同时存活:

#include <vector>
class A { 
public: 
    A(){ cout << this << endl; } 
}; 
int main() { 
    std::vector<A> objs;
    for(int i = 0; i < 2; ++i) {
        objs.emplace_back(); // 每次emplace_back都会创建新对象,地址不同
    }
    return 0; 
}

3. 禁用栈帧复用优化(不推荐)

部分编译器支持禁用栈帧复用的编译选项,比如GCC的-fno-stack-reuse,但这种方法属于编译器特定行为,跨平台性差,而且没有必要为了这个需求修改编译规则,所以不推荐使用。


内容的提问来源于stack exchange,提问作者John Tan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.26 09:39:41