0

我无法理解为什么以下几行在 gcc 中给出了“从不兼容的指针类型初始化”:

int num = 10;
int *p = (char *) #

为什么编译器不清楚我想要这个(当我这样做时,警告消息消失了):

int num = 10;
int *p = (int *) (char *) &num ;

如果以下情况正常:

char eu = (short) 10;

我们不需要这样做:

char eu = (char) (short) 10;

那么为什么我们需要在指针定义中显式添加一个基类型呢?

4

3 回答 3

5

嗯,这只是语言的定义方式:不同类型的对象指针之间不能隐式转换。你需要明确的演员表。

在大多数情况下,取消引用错误类型的指针是未定义的行为因此要求您明确这种类型的转换是一种非常明智的预防措施。

好设计的标志是简单的事情很容易(例如int * p = #),而狡猾的事情是冗长的,因此很明显你在做一些奇怪的事情。

(请注意,在 C(但不是 C++)中,您可以通过void指针进行隐式转换int * p = (void *)#:)

于 2013-09-25T23:42:32.023 回答
2

C 不会隐式地从一种指针类型转换为另一种,除非其中之一是void *. 一般而言,这种转换可能是不可能的。

例如,假设在给定平台上,指向整数的指针必须对齐到四字节边界。您不希望编译器静默尝试将char *可能未对齐的 a 转换为int *.

通过进行显式转换,您可以告诉编译器,“相信我,我知道我在做什么。”

于 2013-09-26T00:01:59.997 回答
0

char eu = (short) 10;没关系,因为它正在分配一个value。如果目标类型可以表示该值,或以定义/有意义的方式(符号扩展、截断、模 2 n)转换该值,则对值的操作始终保留它,但浮点中的特殊值等少数情况除外分配给整数类型时的类型。因此,C 标准允许这些隐式完成,尽管编译器可能会向您发出警告

OTOH 指针直接与底层内存表示相关。例如,您不能通过转换为 int 来访问double*double int*。因此,不允许自动指针转换以防止意外结果。例如,未对齐的访问可能会导致异常或减慢操作,因此禁止隐式转换char*为。int*调用使用不同指针类型访问类型会aliasing调用 UB,编译器也将其用于许多优化。请参阅什么是严格的别名规则?

于 2013-09-26T01:30:56.223 回答