我正在尝试更多地了解 C 及其神秘的隐藏功能,并且我尝试制作一个包含指向 void 的指针的示例结构,旨在用作数组。 编辑:重要提示:这是针对原始 C 代码的。
假设我有这个结构。
typedef struct mystruct {
unsigned char foo;
unsigned int max;
enum data_t type;
void* data;
} mystruct;
我希望数据保存 max 个无符号字符、无符号短整型和无符号长整型,data_t 枚举包含 这 3 种情况的值。
enum Grid_t {gi8, gi16, gi32}; //For 8, 16 and 32 bit uints.
然后我有一个函数来初始化和分配这个结构之一,并且应该返回一个指向新结构的指针。
mystruct* new(unsigned char foo, unsigned int bar, long value) {
mystruct* new;
new = malloc(sizeof(mystruct)); //Allocate space for the struct.
assert(new != NULL);
new->foo = foo;
new->max = bar;
int i;
switch(type){
case gi8: default:
new->data = (unsigned char *)calloc(new->max, sizeof(unsigned char));
assert(new->data != NULL);
for(i = 0; i < new->max; i++){
*((unsigned char*)new->data + i) = (unsigned char)value;
//Can I do anything with the format new->data[n]? I can't seem
//to use the [] shortcut to point to members in this case!
}
break;
}
return new;
}
编译器没有返回任何警告,但我对此方法不太确定。这是使用指针的合法方式吗?
有更好的方法©吗?
我错过了打电话的机会。像 mystruct* P; P = 新(0,50,1024);
union 很有趣,但不是我想要的。因为无论如何我都必须单独处理每个具体案例,所以选角似乎和 union 一样好。我特别希望拥有比 32 位数组大得多的 8 位数组,因此 union 似乎没有帮助。为此,我将其设置为一个长整型数组:P
最佳答案
不可以,您不能取消引用 void*
指针,这是 C 语言标准所禁止的。在执行此操作之前,您必须将其转换为具体的指针类型。
作为替代方案,根据您的需要,您还可以在结构中使用 union
而不是 void*
:
typedef struct mystruct {
unsigned char foo;
unsigned int max;
enum data_t type;
union {
unsigned char *uc;
unsigned short *us;
unsigned int *ui;
} data;
} mystruct;
在任何给定时间,只有 data.uc
、data.us
或 data.ui
之一有效,因为它们都有效在内存中占据相同的空间。然后,您可以使用适当的成员来获取数据数组,而无需从 void*
进行转换。
关于c - 取消引用指向 void 数组的指针,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6947310/