我正在用 C 编写一个用于低级图像处理的基本库。我知道存在其他(非常好的)库;这对我来说是一次学习经历,而不是达到目的的手段。
我已经定义了以下(针对这个问题进行了简化)结构:
union img_rawdata{
uint8_t* u8;
uint16_t* u16;
float* flt;
};
enum img_type{
IMG_U8,
IMG_U16,
IMG_FLT
};
struct image{
union img_rawdata rawdata;
enum img_type type;
unsigned int num_values;
};
我的问题是:在 union 内动态分配正确指针的最佳方式是什么?
现在,我看到的唯一方法是使用 switch 语句,例如:
void alloc_img(struct image* img, enum img_type type, unsigned int num_vals){
switch (type){
case IMG_U8:
img->rawdata.u8 = (uint8_t*)malloc(num_vals*sizeof(uint8_t));
break;
case IMG_U16:
img->rawdata.u16 = (uint16_t*)malloc(num_vals*sizeof(uint16_t));
break;
case IMG_FLT:
img->rawdata.flt = (float*)malloc(num_vals*sizeof(float));
break;
}
}
这看起来还不错;然而,在我的实现中,实际的内存分配大约是 50 行(因为原始数据不是一维的,错误检查等)。
是否有任何可以减少代码冗余的预处理器魔术,或者这是编写此代码的最佳方式吗?
或者,是否有完全不同的方法来解决可以完全避免此问题的问题?
最佳答案
[假设包括void *
在内的所有类型的指针都具有相同的大小]
修改你喜欢的东西
union img_rawdata {
void * untyped;
uint8_t * u8;
uint16_t * u16;
float * flt;
};
enum img_type {
IMG_UNDEF = -1
IMG_U8 = 0,
IMG_U16,
IMG_FLT,
IMG_MAX
};
并添加
const size_t img_type_size[IMG_MAX] = {
sizeof(*((union img_rawdata *) NULL)->u8),
sizeof(*((union img_rawdata *) NULL)->u16),
sizeof(*((union img_rawdata *) NULL)->flt)
};
然后将开关替换为:
assert(IMG_UNDEF < type && IMG_MAX > type);
img->rawdata.untyped = malloc(num_vals * img_type_size[type]);
关于c - 指针 union 的动态分配 - C,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23169171/