首页 > 其他分享 >5.4_C语言类型转换

5.4_C语言类型转换

时间:2023-02-21 09:35:22浏览次数:37  
标签:类型转换 真值 5.4 字节 符号 16 补码 C语言 short

@

目录
这个小结我们要探讨一个相对来说简单的问题,就是 c 语言里边的那些定点整数是如何进行强制类型转换的。

一、案例一

来看这样的一个例子。

首先需要跟大家声明的是, c 语言当中的定点整数,大家熟悉的什么 Int 还有什么 short 还有long,这些定点整数都是用补码的形式来存储的。

另外, c 语言里还有一个关键字叫unsigned,如果用 unsigned 来修饰 short 或者 Int 或者long,那就意味着这个定点整数它是一个无符号数。

现在有一个 short 型的短整数x,它的值是-4321。如下:
image.png

由于是采用补码表示的,并且短整形是占两个字节,也就是 16 个比特,所以 16 个比特的补码表示- 4321 应该是这样的一个值(如下)。这些大家可以自己转换一下。
image.png

原码补码如何转换,我们之前已经强调过,不熟悉的同学可以再自己动手试一下。

现在我们把 x 这个短整形的数强制转换成 unsigned short,也就是无符号的短整形y。这种强制转换的规则是,会把 x 的补码形式的数完整不变的复制给 y 变量

由于 y 也是占两个字节,所以 y 的机器代码其实和 x 是一模一样的。只不过由于 y 是一个无符号的短整形,因此计算机在解析 y 的真值的时候,会按照无符号整数来进行解析。所以把二进制无符号数转换成真值应该是对应值61215。如下:
image.png

这是一个有符号的定点整数,转换成长度相同的无符号定点整数的规则。不改变数据的二进制内容,但是会改变它的解释方式。

二、案例二

再看第二个例子。

如果我们把一个更长的数据,变成一个更短的数据,比如我们定义了两个 Int 型的变量 a 和b。

大多数情况下, c 语言里边 Int 型的数据占 4 个字节。
image.png

现在 a 和 b 是两个有符号的数,都用补码的形式来保存。当我们把 a 和 b 这两个数强制转换成short,也就是由 4 个字节变成 2 个字节的时候,计算机的做法是,直接把高位截断,只保留低位

①a对应的 16 进制应该是这样的(如下),把后四个字节的内容截断,只保留最低两个字节的内容,也就是 86A1。
image.png

更低的两个字节就是 c 变量的值。由于 c 是一个有符号的短整形,所以计算机会用补码的规则来对它进行解析。与之对应的真值应该是-31071这样的值,这是一个 16 比特 16 位的补码。
image.png

②对于 b 和 d 也是一样的, b这个数它用补码表示如下:
image.png

把 b 转换成只有两个字节的 d short 类型,只保留更低的两个字节7751。

同样的,由于 d 它是一个有符号的短整形,所以计算机会用 16 比特补码的方式来对它进行解析,与之对应的真值如下:
image.png

这是更长的数据转换成更短的数据的处理方式。很残暴,直接截断,只保留更低的字节。

三、案例三

最后再来看更短的数据转换成更长的数据。这个问题其实我们之前聊过,也就是所谓符号扩展的问题
image.png

x 原本是一个两个字节的补码,总共占 16 位。

把 short 型的 x 转换成 4 字节的 Int 型。计算机做的事情就是符号扩展

①先来看m变量

之前我们说过,对于一个定点整数的补码来说,如果它是一个负数,我们需要在高位,也就是符号位和原有的数值位之间添1,用这样的方式扩展得到的补码,你把它解析为真值,这个真值是不会变的,只不过是补码的整体长度拓展了而已。
image.png

②再来看n 变量

我们把 x 强制的转换为无符号类型,把它赋值给无符号的短整形n。

之前我们说过,这种强制转换会把二进制代码原封不动的复制给n,只不过计算机会以无符号数的规则来解析这一串机器数,这是 n 所对应的一个真值(如下)。
image.png

③变量p

最后把无符号数 n 变成 4 个字节的无符号数p。

由于是无符号数到无符号数的转变,因此直接在高位填 0 就可以了

p 和 n 的真值,这个真值是保持不变的。如下:
image.png

四、总结

这就是 c 语言里边定点整数相关的一些强制类型转换。
image.png

第一个部分探讨的是在转换的两种数据长度相同的情况下,无符号数和有符号数之间的一种转换规则。

第二个部分探讨的是从长数据强转成短数据的一个处理方式。

第三个部分探讨的是从短数据转为长数据的一个转变方式。

标签:类型转换,真值,5.4,字节,符号,16,补码,C语言,short
From: https://www.cnblogs.com/wanjiadenghuo/p/17139751.html

相关文章

  • C语言语法大纲
    ......
  • c语言程序填空项目
    1.头文件引用2变量的定义和初始化 3常用库函数的使用 4运算符和表达式的使用5实现顺序结构程序设计6用if语句switch语句实现分支结构的程序设计 7用whil......
  • 打卡c语言
    只要是整数,内存中储存的都是二进制的补码正数--原码,反码,补码 相同负数:原码    ---》 反码    --> 补码-2100000000000000000000000000000010......
  • C语言学习中比较奇怪的问题(1)int a = 1 ; int sum = (++a) + (++a) + (++a) ;
    题目:inta=1;  intsum=(++a)+(++a)+(++a); 当前想法:sum=2+3+4= 9 结果:   sum=10 原因:key——寄存器第①个++a......
  • C语言:任意输入三行四列12个整数,如果某行第1个数 2个数都大于等于55,并且第3 4个数都大
    #include<stdio.h>//任意输入三行四列12个整数,如果某行第1个数2个数都大于等于55,并且第34个数都大于等于90,并且该行四个数的和大于等于310则输出"YES"//否则输出"NO......
  • C语言课程设计题目(任选一题)[2023-02-20]
    C语言课程设计题目(任选一题)[2023-02-20]C语言课程设计题目(任选一题)课程设计题目(一):用C语言实现一个图书管理系统,书的信息包括:书名,作者,价格,页数。要求用单链表实现......
  • 类型转换
    ## 类型转换> **二进制**>> 1. 在计算机运算的时候,都是以 **补码** 的方式来运算的。> 2. 二进制 转为 十进制,必须使用 **二进制的原码** 进行转换 。......
  • C语言报错
     在写yacc的时候,用的是CLion编译器,但是测试的时候除了一点问题,在一点一点的打断点测试,但是每一次输入终结符号和非终结符号以及产生式集合很麻烦,于是就用了文件读入上述数......
  • 【Go】类型转换
    字符串转int32packagemainimport( "fmt" "strconv")funcmain(){ str:="12345" num,err:=strconv.ParseInt(str,10,32) iferr!=nil{ fmt.Print......
  • 重学c语言(纯代码)
    //复习自写/*intmain(){//计算1-100中有多少个9 inti=0; intcount=0; for(i=1;i<=100;i++) { if(i%10==9) {  printf("%d",i);  ......