You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

将值溢出signed char的int地址转char*是否为UB及输出结果解析

问题1解答
  • 首先,将任意对象的地址强制转换为char*类型的操作本身不属于未定义行为,这是C标准明确允许的合法操作:标准规定指向对象的指针可转换为字符类型指针,转换后得到的指针指向该对象地址最低的首个字节,通过偏移该字符指针可以遍历访问对象的所有字节表示。
  • 你担心的「数值超出signed char表示范围」的问题,仅在你的编译环境中char默认是signed char类型、且访问到的字节值大于SCHAR_MAX(通常为127)时才会触发,但这种情况属于实现定义行为,不是未定义行为,主流编译器都会按照补码规则直接截断得到对应的有符号值,不会产生不可控的异常。
问题2解答

你的推测完全正确,输出逻辑如下:

  • 300的十六进制表示为0x0000012C,当前主流CPU都是小端序架构,int类型的字节按低位到高位存储,因此地址最低的首个字节值为0x2C,对应十进制数值就是44,ASCII编码中44对应字符,。
  • 执行printf("%d\n", *p)时,直接读取首个字节的整数值输出,因此得到44。
  • 执行printf("%s\n", p)时,因为%s要求传入的是\0结尾的字符串指针,这里你传入的是int对象的字节指针,属于未定义行为,本次输出刚好只有逗号是因为后续字节中很快遇到了值为0的字节,且中间的非0字节是不可打印的控制字符,终端不会显示,所以最终看起来只输出了逗号。

相关建议

  • 不要将非字符串对象的指针直接传给printf的%s占位符,这是明确的未定义行为,可能导致内存越界访问。
  • 如果要检查整数的字节表示,建议显式使用unsigned char*类型转换,避免signed char的符号扩展带来的意料外的结果。
  • 涉及跨架构的字节操作时,要提前判断当前平台的大小端序,避免字节顺序不匹配导致的逻辑错误。

内容的提问来源于stack exchange,提问作者Itachi Uchiwa

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.01 12:57:03