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

C++指针配合new初始化动态多维数组的作用域及段错误问题

问题根因

段错误核心原因是指针传参时值传递的作用域问题,叠加代码多处笔误,具体问题点:

  • init方法的入参double** array是值传递,函数内部给array赋值时,修改的是函数栈上的临时副本,无法修改BaseClass成员变量array的实际值。init执行结束后临时变量销毁,申请的内存地址没有传出,BaseClass::array始终是初始值nullptr,后续dump访问空指针直接触发段错误。
  • 代码存在多处变量名笔误:init入参命名为darray,函数内却操作未定义的array;循环条件错写为s < rows、a < cols;元素赋值时使用未定义的data[i][j]。
  • dump方法实现时未加UtilClass::类作用域限定符,实际定义的是全局函数,不属于类成员。
  • BaseClass.h中include指令缺失#前缀,无法正常编译。
  • 类成员方法默认访问权限为private,未显式声明为public的话,外部无法调用init和dump。
  • 原始代码未做内存释放逻辑,会造成内存泄漏。
修复方案

要让函数内部修改外部的指针,将入参改为指针的引用即可,同时修正所有笔误和访问权限、内存释放问题。

修正头文件

// BaseClass.h
#pragma once
#include "UtilClass.h"

class BaseClass
{
public:
  UtilClass* util{nullptr};
  double** array{nullptr};
  BaseClass();
  ~BaseClass();
};
// UtilClass.h
#pragma once
#include <iostream>

class UtilClass {
public:
  // 入参加&改为引用传递,才能修改外部传入的指针
  void init(double**& array, int rows, int cols);
  void dump(double** array, int rows, int cols);
  void release(double**& array, int rows);
};

修正实现代码

// BaseClass.cpp
#include "BaseClass.h"

BaseClass::BaseClass() {
  util = new UtilClass();
  util->init(array, 4, 6);
  util->dump(array, 4, 6);
}

BaseClass::~BaseClass() {
  util->release(array, 4);
  delete util;
}
// UtilClass.cpp
#include "UtilClass.h"

void UtilClass::init(double **&array, int rows, int cols) {
  int i,j;
  array = new double*[rows];
  for (i = 0; i < rows; i++)
      array[i] = new double[cols];

  // 修正所有变量名笔误
  for (i = 0; i < rows; i++)
      for (j = 0; j < cols; j++) {
          array[i][j] = 1;
          std::cout << "初始化数组元素: " << array[i][j] << std::endl;
      }
}

// 补全类作用域限定符,修正循环花括号缺失问题
void UtilClass::dump(double** array, int rows, int cols) {
  int i, j;
  for (i = 0; i < rows; i++) {
    for (j = 0; j < cols; j++) {
      std::cout << array[i][j] << " ";
    }
    std::cout << std::endl;
  }
}

// 新增内存释放方法避免泄漏
void UtilClass::release(double**& array, int rows) {
  if (!array) return;
  for (int i = 0; i < rows; i++) {
    delete[] array[i];
  }
  delete[] array;
  array = nullptr;
}
优化建议

如果不需要兼容C风格接口,优先使用C++标准库容器管理动态数组,从根源避免指针操作错误:

  • 二维数组直接用std::vector<std::vector<double>>定义,初始化时传入行列参数即可,容器自动管理内存分配和释放,不会出现值传递修改失效的问题。
  • 如果追求内存连续性和访问性能,可以用一维数组模拟二维结构,下标换算为i * cols + j,缓存命中率远高于指针套指针的分段存储结构。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.30 08:33:11