C传递3D数组的2D子集

时间:2014-12-11 23:54:42

标签: c arrays multidimensional-array 3d

我有一个定义为

的3D数组
double ***array

是动态分配的内存。我确定分配是正确的。该数组看起来像这样

array[TDIM][YDIM][XDIM]

我的问题是关于传递/使用数组。函数声明是

void fun(double ***array);

通常,我会进行函数调用并将数组作为

传递
fun(array)

在函数内部我可以更改值。例如

array[0][10][10] = 2.29;

按预期工作。如果我有一个功能,我只想在一个"层"数组而不是传递整个数组...说TDIM == 4 ...我怎么传递那个参数?函数声明是什么样的?如何更改被调用函数中的值?

我尝试了类似这样的东西并且它编译但是看起来很可疑

void fun(double **array)    // function declaration
fun(array[4])               // function call
array[10][10] = 2.29;       // Inside the function, change array[4][10][10] to 2.29

我只想在函数内部处理一个3D数组的2D层,而不必通过整个3D数组,如果这是有意义的话。我可以直接执行此操作,还是必须创建一个临时数组来存储2D图层并使用它?可以使用一些输入。

编辑:添加示例代码以进一步说明。两种方法都一样吗?我觉得我在" fun2"的方法:

void fun(double ***array);  // Declaration
void fun2(double **array);  // Declaration

int main()
{
    double ***array
    int XDIM=10,YDIM=10,TDIM=2;

    allocate3d(&array,XDIM,YDIM,TDIM); // This works fine
    fun(array);
    fun2(array[0]);
}

void fun(double ***array)
{
    for(int j = 0; j < YDIM; j++)
    {
        for(int i = 0; i < XDIM; i++)
        {
            array[0][j][i] = 2.29;
        }
    }
}

void fun2(double **array)
{
    for(int j = 0; j < YDIM; j++)
    {
        for(int i = 0; i < XDIM; i++)
        {
            array[j][i] = 2.29;
        }
    }
}

2 个答案:

答案 0 :(得分:1)

最好提供一个工作示例..有许多缺失的部分可能在某种程度上是错误的(例如变量XDIMYDIM,..)。很难理解你想要做什么。

假设funfun2的任务是在用户传递的单元格中写入值2.29,那么您的fun方法不会产生很多感觉..你如何通过索引?你在方法中使用了0 ..这个改变怎么样:

void fun(double ***array, int idx)
{
    for(int j = 0; j < YDIM; j++)
    {
        for(int i = 0; i < XDIM; i++)
        {
            array[idx][j][i] = 2.29;
        }
    }
}

评论后编辑:一个三维数组看起来像一个二维数组的数组,它在内存中是连续的:

int array3d[2][2][2] = {{{0, 1}, {2, 3}},{{4, 5}, {6, 8}}};

在内存中是这样的:

0 1 2 3 4 5 6 7

与声明完全相同:

int array1d[8] = { 0, 1, 2, 3, 4, 5, 6, 7 };

因此,您的方法是正确的,因为您正在更改相同的内存位置。

答案 1 :(得分:1)

你只是按照自己的方式去做。您的原始程序似乎存在一些问题,您认为XDIMYDIM是全局的,但它们似乎不是。

这将按预期工作:

#include <stdio.h>
#include <stdlib.h>

struct tda {
    double *** data;
    int x;
    int y;
    int z;
};

struct tda * tda_allocate(const int x, const int y, const int z);
void tda_destroy(struct tda * array);
void tda_fill_level(double ** data, const int x, const int y,
                    const double value);
void tda_print(struct tda * array);

int main(void)
{
    struct tda * array = tda_allocate(3, 2, 2);

    for ( int i = 0; i < array->x; ++i ) {
        tda_fill_level(array->data[i], array->y, array->z, i + 1);
    }

    tda_print(array);
    tda_destroy(array);

    return 0;
}

struct tda * tda_allocate(const int x, const int y, const int z)
{
    struct tda * new_array = malloc(sizeof *new_array);
    if ( !new_array ) {
        perror("couldn't allocate memory");
        exit(EXIT_FAILURE);
    }

    double *** new_data = malloc(x * sizeof *new_data);
    if ( !new_data ) {
        perror("couldn't allocate memory");
        exit(EXIT_FAILURE);
    }

    for ( int i = 0; i < x; ++i ) {
        new_data[i] = malloc(y * sizeof *new_data[i]);
        if ( !new_data[i] ) {
            perror("couldn't allocate memory");
            exit(EXIT_FAILURE);
        }

        for ( int j = 0; j < y; ++j ) {
            new_data[i][j] = malloc(z * sizeof *new_data[i][j]);
            if ( !new_data[i][j] ) {
                perror("couldn't allocate memory");
                exit(EXIT_FAILURE);
            }
        }
    }

    new_array->data = new_data;
    new_array->x = x;
    new_array->y = y;
    new_array->z = z;

    return new_array;
}

void tda_destroy(struct tda * array)
{
    for ( int i = 0; i < array->x; ++i ) {
        for ( int j = 0; j < array->y; ++j ) {
            free(array->data[i][j]);
        }
        free(array->data[i]);
    }
    free(array->data);
    free(array);
}


void tda_fill_level(double ** data, const int x, const int y,
                    const double value)
{
    for ( int i = 0; i < x; ++i ) {
        for ( int j = 0; j < y; ++j ) {
            data[i][j] = value;
        }
    }
}

void tda_print(struct tda * array)
{
    for ( int i = 0; i < array->x; ++i ) {
        for ( int j = 0; j < array->y; ++j ) {
            for ( int k = 0; k < array->z; ++k ) {
                printf("%2d,%2d,%2d: %f\n", i, j, k, array->data[i][j][k]);
            }
        }
    }
}

带输出:

paul@thoth:~/src/sandbox$ ./tda
 0, 0, 0: 1.000000
 0, 0, 1: 1.000000
 0, 1, 0: 1.000000
 0, 1, 1: 1.000000
 1, 0, 0: 2.000000
 1, 0, 1: 2.000000
 1, 1, 0: 2.000000
 1, 1, 1: 2.000000
 2, 0, 0: 3.000000
 2, 0, 1: 3.000000
 2, 1, 0: 3.000000
 2, 1, 1: 3.000000
paul@thoth:~/src/sandbox$