转换void指针

Bla*_*iev 17 c pointers void-pointers

我在旧的C代码中看到了很多以下内容:

type_t *x = (type_t *) malloc(...);
Run Code Online (Sandbox Code Playgroud)

从那里malloc()开始返回指针的重点是什么void *?是因为较旧的C编译器不支持void指针而是malloc()习惯返回char *

sch*_*hot 23

你自己的解释是正确的.预ANSI C('K&R'C)没有void *隐式转换的类型.char *double作为伪void *类型,但您需要显式转换类型转换.

在现代C中,演员阵容不受欢迎,因为它可以抑制编译器警告缺少原型malloc.在C++中,需要进行转换(但是你应该使用new而不是malloc大部分时间).

更新

我在下面的评论试图解释为什么需要演员表有点不清楚,我会在这里尝试更好地解释它.您可能会认为即使malloc返回时char *也不需要强制转换,因为它类似于:

int  *a;
char *b = a;
Run Code Online (Sandbox Code Playgroud)

但在这个例子中,还需要演员.第二行是简单赋值运算符(C99 6.5.1.6.1)的约束违例.两个指针操作数都需要是兼容类型.当您将其更改为:

int  *a;
char *b = (char *) a;
Run Code Online (Sandbox Code Playgroud)

约束违反消失(两个操作数现在都有类型char *),结果定义明确(转换为char指针).在"反向情况":

char *c;
int  *d = (int *) c;
Run Code Online (Sandbox Code Playgroud)

相同的参数保持为强制转换,但是当int *具有比更严格的对齐要求时char *,结果是实现定义的.

结论:在ANSI之前的日子里,类型转换是必要的,因为malloc返回char *而不是转换结果是对'='运算符的约束违反.


sla*_*ker 6

这里的问题是与C的任何方言不兼容.问题是C++.在C++中,void指针不能自动转换为任何其他指针类型.因此,如果没有显式强制转换,此代码将无法使用C++编译器进行编译.