Skip to content

野指针的写法

以下是可能导致野指针的程序写法:

1. 指针变量没有初始化

错误示例

int* ptr;
*ptr = 5;

正确用法

int* ptr = new int;
*ptr = 5;
// 做完操作后再delete ptr;

正确用法-智能指针

std::unique_ptr<int> ptr(new int);
*ptr = 5;
// 可以不用显式delete,智能指针在作用域结束时自动释放

2. 使用已释放的指针

错误示例

int* ptr = new int;
delete ptr;
*ptr = 5;

正确用法

int* ptr = new int;
delete ptr;
ptr = nullptr; // 把指针置为 nullptr 避免野指针

正确用法-智能指针

std::unique_ptr<int> ptr(new int);
ptr.reset(); // 通过调用 reset() 方法,将智能指针置空

3. 未正确分配内存

错误示例

int* ptr = new int[5];
ptr = new int[10];
delete[] ptr;

正确用法

int* ptr = new int[5];
delete[] ptr;
ptr = new int[10];
// 做完操作后再 delete[] ptr;

正确用法-智能指针

std::unique_ptr<int[]> ptr(new int[5]);
// 智能指针在作用域结束时自动释放它所指向的内存

4. 返回被释放的堆栈变量的指针

错误示例

int* get_pointer() {
   int value = 5;
   int* ptr = &value;
   return ptr;
}

int* ptr = get_pointer();
*ptr = 10;

正确用法

int* get_pointer() {
   int* ptr = new int;
   *ptr = 5;
   return ptr;
}
int* ptr = get_pointer();
// 做完操作后再 delete ptr;

正确用法-智能指针

std::unique_ptr<int> get_pointer() {
   return std::make_unique<int>(5); //使用 std::make_unique 分配内存
}

std::unique_ptr<int> ptr = get_pointer();

5. 越界访问数组

错误示例

int* ptr = new int[5];
ptr[5] = 5;

正确用法

int* ptr = new int[5];
ptr[4] = 5; // 应该将下标限制在 0 到 4 之间
// 做完操作后再 delete[] ptr;

正确用法-智能指针

std::vector<int> vec(5);
vec[4] = 5;
// 在作用域结束时,vec会自动释放其内存

6. 当作整数使用指向对象的指针

错误示例

class MyClass {
public:
   int value;
};

MyClass* ptr = new MyClass;
int value = *reinterpret_cast<int*>(ptr);

正确用法

class MyClass {
public:
   int value;
};

MyClass* ptr = new MyClass;
int value = ptr->value; // 或者使用 reinterpret_cast<int*>(ptr) 来安全地转换指针类型
// 做完操作后再 delete ptr;

正确用法-智能指针

class MyClass {
public:
   int value;
};

std::shared_ptr<MyClass> ptr = std::make_shared<MyClass>();
int value = ptr->value;
// 在作用域结束时,ptr会自动释放其内存