C-在没有其他成员的结构内的动态阵列大小表示大小



我的结构定义为:

struct Voxel1
{
   float array[16];
};

以后我可以将图像分配为指定数量数量体素的连续内存,例如,

int voxelNum = 1000;
Voxel1* image = (Voxel1*)calloc(voxelNum, sizeof(Voxel1));

然后,我可以访问sizeof(Voxel1)的连续内存进行一些操作,例如,

Voxel1 a;
//do some computation on a, 
//copy it to the 101-th voxel in the image
image[100] = a;

我的问题是,稍后我决定在运行时确定数组的大小,即Voxel1中的数组成员具有动态大小。有什么方法可以做到吗?我的要求是,我不想保存其他成员来指示数组的大小,如下所示:

struct Voxel2
{
   size_t size;
   float* array;
}IDontWantThisDefinition;

由于此额外的成员,后来我的实际voxel2大小将是sizeof(float)*size+sizeof(size_t),现在我尝试修改体素值时,它们不像以前那样连续。

我想要的是一些定义(我知道voxel3是无效的)具有以下定义,除了可以在运行时确定size

struct Voxel3
{
   //so I want size to be static so that it does not take memory on the stack
   //also I want it to be const so that it can be used to define array's size
   static const size_t size;
   float array[size];
}DesireButInvalidDefinition;

在程序中,我可以做这样的事情:

int main(int argc, char** argv)
{
    int arraysize = 32;
    //allocate 1000 voxels where each voxel has 32 float element
    Voxel3* image = (Voxel3*)calloc(1000, sizeof(Voxel3));
    Voxel3 anotherVoxel;
    image[100]=anotherVoxel;
}

我不确定是否有任何解决方案可以满足这种设计,或者设计可以做一些与我想要的事情。预先感谢。

很难说是什么是最好的方法,但是正如我在最高评论中提到的那样,将大小移动结构定义。

首先,您必须在执行任何操作之前计算动态大小。

int voxel_size;                         // dynamically computed
typedef struct _Voxel {
    float *array;                       // count is voxel_size
} Voxel;
typedef struct _VoxelArray {
    int count;
    Voxel *voxels;
} VoxelArray;
void
voxel_init(Voxel *vox)
{
    vox->array = calloc(voxel_size,sizeof(float));
}
Voxel *
voxel_alloc(int count)
{
    Voxel *vox;
    vox = calloc(count,sizeof(voxel));
    for (int idx = 0;  idx < count;  ++idx)
        voxel_init(vox + idx);
    return vox;
}
VoxelArray *
voxel_array(VoxelArray *arr,int count)
{
    if (arr == NULL)
        arr = calloc(1,sizeof(VoxelArray));
    arr->count = count;
    arr->voxels = voxel_alloc(count);
    return arr;
}
int
main(int argc, char** argv)
{
    voxel_size = 32;
    Voxel anotherVoxel;
    voxel_init(&anotherVoxel);
    //allocate 1000 voxels where each voxel has 32 float element
    Voxel *image = voxel_alloc(1000);
    image[100] = anotherVoxel;
    VoxelArray varray;
    voxel_array(&varray,1000);
    varray.voxels[100] = anotherVoxel;
    VoxelArray *varrptr = voxel_array(NULL,1000);
    varrptr->voxels[100] = anotherVoxel;
    return 0;
}

通过分开数据和数据访问者,这就是我得到的。不过,这不是内存管理的一个很好的例子。

#include <cstddef>
#include <cstdlib>
// Both Voxel3 and Voxel3Image are just data accessors,
// which provide a way to access the real data.
struct Voxel3
{
    static size_t size;
    float *array;
    Voxel3(float *data = nullptr) {
        array = data;
    }
    // 'image[100]=anotherVoxel;' won't do the right
    // thing(deep copy) without this.
    Voxel3 & operator = (const Voxel3 &v) {
        for (size_t i = 0; i < size; ++i)
            array[i] = v.array[i];
        return *this;
    }
};
size_t Voxel3::size;
// you want image[100], use this.
struct Voxel3Image
{
    float *data_ref;
    Voxel3Image(float *data = nullptr) {
        data_ref = data;
    }
    // image[100] need this.
    Voxel3 operator [] (int i) {
        return Voxel3(data_ref + i * Voxel3::size);
    }
};
int main(int argc, char** argv)
{
    Voxel3::size = 32;
    float *real_data = (float*)calloc(1000,
                                      sizeof(float) * Voxel3::size);
                                      // sizeof(Voxel3) == sizeof(float *),
                                      // not what your want.
    // allocate 1000 voxels where each voxel has 32 float element
    Voxel3Image image( real_data );
    Voxel3 anotherVoxel;
    // initialize anotherVoxel
    image[100]=anotherVoxel;
    return 0;
}

最新更新