C++智能指针实现问题求助:输出结果不符合预期
解决你的C++智能指针输出异常问题
兄弟,你这输出问题一看就是智能指针的内部资源管理彻底乱了——要么是没做引用计数,要么是拷贝/赋值逻辑写错了,导致两个指针抢同一块内存,还出现了野指针(那个4919984就是野指针读出来的垃圾值)。
先给你看修正后的完整代码,保证能输出预期的intOne: 1 intTwo: 10:
#include <stdio.h> #include <stdlib.h> #include <iostream> #include <exception> using namespace std; template <typename T> class SmartPointer { private: T* ptr; size_t* ref_count; // 用引用计数跟踪资源被多少指针共享 // 辅助函数:释放当前持有的资源 void release() { if (ref_count) { (*ref_count)--; // 引用计数归0时才真正释放内存 if (*ref_count == 0) { delete ptr; delete ref_count; } } // 重置指针,避免野指针 ptr = nullptr; ref_count = nullptr; } public: // 基础构造函数:接收原始指针 explicit SmartPointer(T* p = nullptr) : ptr(p) { if (ptr) { ref_count = new size_t(1); // 新资源引用计数初始为1 } else { ref_count = nullptr; } } // 拷贝构造:共享资源,增加引用计数 SmartPointer(const SmartPointer& other) { ptr = other.ptr; ref_count = other.ref_count; if (ref_count) { (*ref_count)++; } } // 赋值运算符:先释放自己的资源,再共享新资源 SmartPointer& operator=(const SmartPointer& other) { if (this != &other) { // 防止自赋值搞崩资源 release(); ptr = other.ptr; ref_count = other.ref_count; if (ref_count) { (*ref_count)++; } } return *this; } // 移动构造(可选,提升性能,避免不必要的计数操作) SmartPointer(SmartPointer&& other) noexcept { ptr = other.ptr; ref_count = other.ref_count; // 把原对象的指针置空,避免它析构时释放资源 other.ptr = nullptr; other.ref_count = nullptr; } // 移动赋值(可选) SmartPointer& operator=(SmartPointer&& other) noexcept { if (this != &other) { release(); ptr = other.ptr; ref_count = other.ref_count; other.ptr = nullptr; other.ref_count = nullptr; } return *this; } // 解引用运算符:安全访问对象 T& operator*() const { if (!ptr) { throw runtime_error("别解引用空指针啊兄弟!"); } return *ptr; } // 箭头运算符:访问对象成员 T* operator->() const { if (!ptr) { throw runtime_error("空指针不能用->!"); } return ptr; } // 获取原始指针(谨慎使用,别乱搞) T* get() const { return ptr; } // 析构函数:清理资源 ~SmartPointer() { release(); } }; int main() { SmartPointer<int> intOne(new int(1)); SmartPointer<int> intTwo(new int(3)); *intTwo = 10; // 是修改指针指向的对象的值,不是直接给智能指针赋值新指针! cout << "intOne: " << *intOne << " intTwo: " << *intTwo << endl; return 0; }
说说你之前代码的核心问题:
- 没做引用计数:如果你的SmartPointer只是简单持有原始指针,没跟踪共享数量,拷贝/赋值时多个对象会指向同一块内存,修改一个就会影响另一个,析构时还会重复释放内存导致野指针。
- 赋值逻辑错误:如果你直接给智能指针赋值新原始指针(比如
intTwo = new int(10)),但没重载赋值运算符,会导致原内存泄漏,新内存管理混乱。正确做法要么是修改已有对象的值(*intTwo = 10),要么赋值新的智能指针对象(这时候需要重载运算符处理引用计数)。 - 野指针访问:那个4919984就是因为某个指针指向的内存已被释放,但你还在访问,读出来的垃圾值。
实现智能指针的关键要点:
- 必须用引用计数跟踪资源共享情况,只有最后一个指针销毁时才释放内存。
- 必须实现拷贝构造函数和赋值运算符重载,默认浅拷贝会直接复制指针,导致资源管理崩溃。
- 可选实现移动语义,提升性能,避免不必要的引用计数操作。
- 解引用和箭头运算符要做空指针检查,避免程序崩溃。
内容的提问来源于stack exchange,提问作者IWantToDie
相关产品推荐
相关产品推荐

