在声明数组时使用星号

时间:2012-01-26 04:26:39

标签: pointers multidimensional-array constants

我有两个关于多维数组的问题。我使用两颗星声明了一个3D数组,但是当我尝试访问这些元素时,我得到了一个无用的初始化错误。

unsigned **(test[10]);
**(test[0]) = 5;

当我使用下面的代码时,我得到了这个错误,我没有收到错误 - 有什么区别?

unsigned test3[10][10][10];
**(test3[0]) = 5;

我的第二个问题是:我正在尝试将一段为Unix编写的代码移植到Windows。其中一条就是:

unsigned **(precomputedHashesOfULSHs[nnStruct->nHFTuples]);

* nHFTuples的类型为int,但它不是常量,这是我得到的错误;

error C2057: expected constant expression

我是否可能收到此错误,因为我在Windows上运行它而不是Unix? - 我怎么解决这个问题?我无法使nHFTuples成为常量,因为用户需要为它提供值!

2 个答案:

答案 0 :(得分:3)

在第一个中,你没有声明一个3D数组,你声明了一个指向无符号整数的10个指针的数组。当您取消引用它时,您将取消引用垃圾指针。

在第二个中,你正确地声明了数组但是你使用它错了。数组不是指针,你不会取消引用它们。

这样做:

unsigned test3[10][10][10];
test3[0][0][0] = 5;

要回答第二个问题,必须使用编译时可以知道的数字作为数组的大小。 GCC有一个非标准的扩展,允许你这样做,但它不是可移植的,不是标准的一部分(虽然C99引入了它们)。要解决此问题,您必须使用mallocfree

int i, j, k;

unsigned*** precomputedHashOfULSHs = malloc(nnStruct->nHFTuples * sizeof(unsigned));

for (i = 0; i < firstDimensionLength; ++i) {
    precomputedHashOfULSHs[i] = malloc(sizeOfFirstDimension * sizeof(unsigned));

    for (j = 0; j < secondDimensionLength; ++j) {
        precomputedHashOfULSHs[i][j] = malloc(sizeOfSecondDimension * sizeof(unsigned));

        for (k = 0; k < sizeOfSecondDimension; ++k)
            precomputedHashOfULSHs[i][j][k] = malloc(sizeof(unsigned));
    }
}

// then when you're done...

for (i = 0; i < firstDimensionLength; ++i) {
    for (j = 0; j < secondDimensionLength; ++j) {
        for (k = 0; k < sizeOfSecondDimension; ++k)
            free(precomputedHashOfULSHs[i][j][k]);

        free(precomputedHashOfULSHs[i][j]);
    }

    free(precomputedHashOfULSHs[i]);
}

free(precomputedHashOfULSHs);

(请原谅我,如果分配/解除分配代码错误,已经很晚了))

答案 1 :(得分:1)

虽然你没有指定它,但我认为你在支持C99(SUch作为GCC)的unix上使用编译器,而你在windows上使用的编译器不支持它。 (Visual Studio此处仅使用C89。)

您有三种选择:

  1. 您可以硬编码合适的最大阵列大小。
  2. 您可以使用malloc或calloc自行分配数组。完成后不要忘记释放它。
  3. 将程序移植到C ++,并使用std :: vector。
  4. 如果您选择选项3,那么您需要以下内容:

    std::vector<unsigned int> precomputedHashOfULSHs;
    

    对于单维向量或二维向量,请使用:

    std::vector<std::vector<unsigned int> > precomputedHashOfULSHs;
    

    请注意,向量默认为空,长度为零,因此您需要添加原始集中的每个元素。

    以test3为例,您需要:

    std::vector<std::vector<std::vector<unsigned int> > > precomputedHashOfULSHs;
    precomputedHashOfULSHs.resize(10);
    for(int i = 0; i < 10; i++) {
        precomputedHashOfULSHs[i].resize(10);
        for(int ii=0; ii<10; ii++) {
            precomputedHashOfULSHs[i][ii].resize(10);
        }
    }
    

    我没有测试过这段代码,但它应该是正确的。 C ++将自动为您管理该向量的内存。