用(void **)传递(double ***)指针可以吗?

问题描述 投票:0回答:1

我在编译下面的代码时使用了 gcc 使用 -Wall -Werror 而且编译得很干净,运行得很正常;但是,我只是好奇,在 美国国家标准协会ISO C 上下文中,传递一个 (double ***) 指针 (void **).

ISOIEC 9899:2017第6.6-9节说

"数组脚本 [] 和成员访问 .-> 操作员,地址 & 和间接性 * 单元运算符,以及 指针投掷 可用于创建地址常数,但不得通过使用这些运算符来访问对象的值"。

"关于这项建议,函数 allocateMatrix 事实上,应该是 只是 分配内存并返回相应的地址;所以,请忽略分配值的内部循环,它只是为了测试目的。

void allocateMatrix(int n, void **a) {
    int i = 0, j = 0;
    double **pTmp = calloc(n, sizeof(double *));

    for (i = 0; i < n; i++) {
        pTmp[i] = malloc(n * sizeof(double));

        // following loop is inserted to make sure code runs as expected
        // this does not exists in real code
        for (j = 0; j < n; j++) {
            pTmp[i][j] = (double)(i + 1) + (double)(j + 1) / 10.0f;
        }
    }

    *a = pTmp;
    return;
}

int main(int argc, char const *argv[]) {
    int i = 0, j = 0;
    int n = 5;
    double **a = NULL;

    // "a" is a (double **) pointer; so, "&a" is now a (double ***) pointer
    allocateMatrix(n, (void **)&a);

    // testing...
    for (i = 0; i < n; i++) {
        for (j = 0; j < n; j++) {
            printf("%6.2lf", a[i][j]);
        }

        printf("\n");
    }

    return 0;
}
c pointers iso
1个回答
4
投票

C标准允许转换为和从 void *然而,该律师并 有的是 void **.

将函数参数改为 void * 并将其适当地转码,就可以使用了。

void allocateMatrix(int n, void *a) {
    ...
    *(double ***)a = pTmp;
}

并将函数调用中的cast改为删除。

allocateMatrix(n, &a);
© www.soinside.com 2019 - 2024. All rights reserved.