使用/指针创建3D数组时的分段错误(核心转储)

时间:2014-01-25 02:44:29

标签: c++ arrays pointers multidimensional-array

提前感谢您的帮助!

我目前正在通过Alex Allain的“跳入C ++”工作,到目前为止,它是一本很棒的书,就C ++中的速成课程而言。至少对我而言。任何我在第14章讨论使用2D数组指针和其中一个实践问题都要求读者创建一个3D乘法表数组,其中包含用户在运行时选择的任意长度,宽度和高度。我想我已经有了代码和工作,感谢有人在这里我能够摆脱与使用指针创建3D数组相关的所有编译错误。

我会发布我的问题图片,但当然我的声誉不够高。基本上在我编译并运行程序之后,我为3D数组的高度,宽度和深度输入了3个单独的维度,然后我得到了令人兴奋的消息“Segmentation fault(core dumped)。我的代码中有一些调试cout消息但是没有一个出现让我感到困惑。我不明白为什么我的代码最早会在第一个调试消息之前崩溃。唯一一次它在任何地方都是如果我为所有三个值输入1。但是那时只有调试消息显示出来,并没有像我认为的那样实际打印。

这是我的代码:

#include <iostream>

using namespace std;

void printMultTable(int*** p_cube, int height, int width, int depth);

int main() {
    int height = 0;
    int width = 0;
    int depth = 0;

    // Get user input for height, witdth, and depth of multiplication cube
    cout << "Enter height:  ";
    cin >> height;

    cout << "Enter width:  ";
    cin >> width;

    cout << "Enter depth:  ";
    cin >> depth;

    cout << "Made it to point A";

    // Create pointer to pointer for multiplication tables
    int ***p_cube = new int**[depth]; // Creates pointer to 2D pointer array (Layers of Cube)

    cout << "Made it to point B";

    for (int i = 0; i < height; i ++) {
        p_cube[i] = new int*[height]; // Creates pointer to 1D array (Columns of Cube)
        for (int j = 0; i < width; i++) {
            p_cube[i][j] = new int[width]; // Creats pointers that are arrays (Rows of Cube)
        }
    }

    cout << "Made it to point C";


    // Create multiplication table
    for (int i = 0; i < depth; i++) {
        for (int j = 0; j < height; j++) {
            for (int k = 0; k < width; k++) {
                p_cube[i][j][k] = (j+1) * (k+1);
            }
        }
    }

    cout << "Made it to point D";

    // Use printMultTable to print out multiplication table
    printMultTable(p_cube, height, width, depth);

    // Deallocate memory taken by pointers
    for (int i = 0; i < height; i++) {
        for (int j = 0; j < width; j++){
            delete[] p_cube[i][j];
        }
        delete p_cube[i];
    }
    delete[] p_cube;
}

void printMultTable(int*** p_cube, int height,int width,int depth) {
    for (int i = 0; i < depth; i++) {
        for (int j = 0; j < height; j++) {
            for (int k = 0; k < width; k++) {
                cout << p_cube[i][j][k] << "\t";
            }
            cout << "\n";
        }
        cout << "\n\n\n";
    }
}

正如您可能会注意到我有4个单独的调试检查点,上面写着“使它成为点__”。问题是它甚至没有指向“A”。我不确定这是否是编译器跳过的错误,因为它认为代码是犹太的,或者它与我的计算机或其他我无法想到的东西。指针必须是最令人困惑的事情,几乎有意义,我曾经学过哈哈。

非常感谢任何和所有的帮助或想法!

谢谢! 扎克

3 个答案:

答案 0 :(得分:0)

此代码:

for (int i = 0; i < height; i ++) {
    p_cube[i] = new int*[height]; // Creates pointer to 1D array (Columns of Cube)
    for (int j = 0; i < width; i++) {
        p_cube[i][j] = new int[width]; // Creats pointers that are arrays (Rows of Cube)
    }
}

应该是:

for (int i = 0; i < depth; i ++) {
    p_cube[i] = new int*[height]; // Creates pointer to 1D array (Columns of Cube)
    for (int j = 0; j < height; j++) {
        p_cube[i][j] = new int[width]; // Creats pointers that are arrays (Rows of Cube)
    }
}
  • first for循环必须从0到depth
  • 第二个for循环必须从0到height
  • 您在第二个for循环中比较并增加了i而不是j

答案 1 :(得分:0)

显而易见的问题是,当height个对象存在时,您使用depth作为第一个循环的范围。

int ***p_cube = new int**[depth];
// ...
for (int i = 0; i < height; i ++) {
    p_cube[i] = new int*[height];
    // ...
}

如果depth != height您将拥有超出限制的访问权限,或者您将访问未初始化的内存。

另一个问题是你不检查你的积分是一个非常坏主意!如果输入失败,您将获得随机值。在阅读之后一定要检查它是否成功:

if (std::cin >> depth) { ... }

如果这本书的作者提倡赤裸裸的分配和未经检查的读物,他会给你带来很大的伤害!

答案 2 :(得分:0)

祝你好运!

首先,我认为像这样学习int ***不是一个好的开始方式,因为它非常混乱且效率低下。我建议只使用width * height * depth元素分配一块内存。要遍历元素,您可以简单地从[0 .. width * height * depth]迭代索引。要访问特定元素,您可以像这样计算:index = i *(width * height)+ j *(width)+ k。

但为了回答你的问题,我注意到你在这里犯了一个错误:

int ***p_cube = new int**[depth];
for (int i = 0; i < height; i ++) {
    p_cube[i] = new int*[height];
    ...

你已经创建了一个大小为'depth'的int **的新数组,但是你迭代它就好像它有'height'元素一样。正确的做法是迭代'depth'元素,并分配一个int *数组。