c/c++语言开发共享不在C中转换指针会导致问题?

昨天我上课了,在某个时候讲师正在谈论C代码。 他说:

在C中制作指针的目的是什么? 唯一的目的是使编译器正确解释指针操作(例如,添加int指针将导致与添加char指针不同的偏移量)。 除此之外,没有区别:所有指针在内存中的表示方式相同,无论指针指向int值,char值,short值等等。 因此,转换指针不会修改内存中的任何内容,它只会帮助程序员执行与他正在处理的指针类型更相关的操作。

但是,我已经阅读,特别是在Stack Overflow中,这不是100%真实。 我已经读过,在一些奇怪的机器中,不同类型的指针可以以不同的方式存储在内存中。 在这种情况下,如果将代码编译为此类机器,则不将指针更改为正确的类型可能会导致问题。

基本上,这是我正在谈论的那种代码。 考虑以下代码:

int* int_pointer; char* char_pointer; int_pointer = malloc(sizeof(int)); *int_pointer = 4; 

现在有两种选择:

1。

 char_pointer = (char *)int_pointer; 

2。

 char_pointer = int_pointer; 

案例2的代码可能成为一个问题? 制作演员表(案例1)最终会改变内存中的指针格式(如果是的话,你能给出一个机器的例子吗?)?

谢谢

    您的讲师所说的关于共享相同表示的所有指针类型通常适用于C语言的实际实现。

    但是,从抽象C语言本身的角度来看,这是不正确的。 C语言保证

    就这些。 没有其他保证。 这意味着就语言本身而言, int *指针具有与double *指针不同的表示。 而指向struct S指针与指向union U指针的表示方式不同。

    但是,如图所示,使用char_pointerint_pointer示例并不完全是说明性的。 char_pointer = int_pointer; 赋值只是无效(如“不编译”)。 语言不支持不兼容的指针类型之间的隐式转换。 此类转换始终需要显式强制转换运算符。

    不在C中转换指针会导致问题?

    C中的指针类型之间没有隐式转换(例如,在算术类型之间) – 具有void *类型的exception。 这意味着如果要将指针转换为另一种指针类型( void *除外),则C要求您进行转换。 如果您不这样做,则需要实施以发出诊断消息,并且允许转换失败。

    有些编译器足够好(或变态不够),不需要强制转换。 它们通常表现得就像你明确地放置了演员表。

      char *p = NULL; int *q = NULL; p = q; // not valid in C 

    总之,出于可移植性原因,在将指针转换为指针时应始终放置强制转换。

    编辑:

    外部可移植性,一个不进行强制转换的示例可能会导致您遇到实际问题,例如使用可变参数函数。 让我们假设一个实现,其中char *的大小大于int *的大小。 假设函数期望一个参数的类型为char * 。 如果要传递int *的参数,则必须将其转换为char * 。 如果你没有强制转换它,当函数访问char *对象时,对象的某些位将具有不确定的值,并且bevahior将是未定义的。

    一个有点接近的例子是printf ,如果用户无法转换为void *转换说明符的参数void * ,C表示它会调用未定义的行为。

    你的教授说的听起来是对的。

    …(例如,添加int指针将导致与添加char指针不同的偏移量)

    这是正确的,因为假设int是4个字节而char是1个字节,向int指针添加2将导致将指针移动8个字节,而向char指针添加2将仅将指针移动到下一个字节2立场。

    除此之外,没有区别:所有指针在内存中的表示方式相同,无论指针指向int值,char值,short值等等。

    这是事实,机器不区分char和int指针,这些是编译器要处理的问题。 你的教授也提到了:

    唯一的目的是使编译器正确解释指针操作

    因此,转换指针不会修改内存中的任何内容,它只会帮助程序员执行与他正在处理的指针类型更相关的操作。

    这也是事实。 转换不会修改内存,只会更改内存的一部分解释方式。

    转换指针不会改变指针值,它只告诉编译器如何处理指针。 指针本身只是一个数字,它没有类型。 它是存储具有类型的指针的变量。

    两种分配指针的方法没有区别(如果编译器允许你进行分配)。 无论源指针变量的类型如何,都将根据赋值后的目标变量的类型使用指针。

    您根本无法将int指针存储在char指针变量中。 一旦值存储在变量中,它就没有一个指向int的指针。

    直接使用值时,强制转换指针很重要,例如:

     int* int_pointer; int_pointer = malloc(sizeof(int)); *int_pointer = 4; char c; c = *(char*)int_pointer; 

    转换指针意味着取消引用它会从该位置读取char,而不是int。

    从void *转换到我的程序中需要的类型(例如int *,char *,struct x *)对我来说很有意义。 但是,跨越其他类型(即int *到char *等)的转换可能会成为问题(由于int,char等的偏移量不同)。 如果这样做,请小心。

    但是……要专门回答您的问题,请考虑以下事项:

     int_pointer = malloc(2 * sizeof(int)); // 2 * 4 bytes on my system. *int_pointer = 44; *(int_pointer + 1 )= 55; printf("Value at int_pointer = %dn", *int_pointer); // 44 printf("Value at int_pointer + 1 = %dn", *(int_pointer + 1)); // 55 

    (上面的偏移量将以4个字节为增量。)

     //char_pointer = int_pointer; // Gives a warning ... char_pointer = (char*)int_pointer; // No warning. printf("Value at char_pointer = %dn", *char_pointer); // 0 printf("Value at char_pointer = %dn", *(char_pointer+1)); // 0 printf("Value at char_pointer = %dn", *(char_pointer+2)); // 0 printf("Value at char_pointer = %dn", *(char_pointer+3)); // 44 <== 

    四个字节被分配给int值44.44的二进制表示是00101100 ...剩余的3个字节都是0。 因此,当使用char *指针访问时,我们一次增加1个字节并获得上述值。

    指针的转换对于说编译器如何执行指针运算至关重要。

    例如,如果x是指向内存2001的字符指针,x ++应该转到2002,但如果x是一个整数指针x ++应该是2003

    因此,如果未对指针进行类型转换,则编译器将无法正确执行指针arithematic。

    需要了解更多c/c++开发分享不在C中转换指针会导致问题?,也可以关注C/ C++技术分享栏目---计算机技术网(www.ctvol.com)!

      以上就是c/c++开发分享不在C中转换指针会导致问题?相关内容,想了解更多C/C++开发(异常处理)及C/C++游戏开发关注计算机技术网(www.ctvol.com)!)。

      本文来自网络收集,不代表计算机技术网立场,如涉及侵权请联系管理员删除。

      ctvol管理联系方式QQ:251552304

      本文章地址:https://www.ctvol.com/c-cdevelopment/979871.html

      (0)
      上一篇 2021年12月13日
      下一篇 2021年12月13日

      精彩推荐