码迷,mamicode.com
首页 > 编程语言 > 详细

C语言的有符号与无符号,二进制整数的扩展与截断

时间:2015-08-14 11:50:58      阅读:124      评论:0      收藏:0      [点我收藏+]

标签:计算机   计算机科学   

C语言的有符号与无符号,二进制整数的扩展与截断

 

 

前一节说了整数的表示方式,,也就是无符号编码与补码编码.这一届说一下二进制整数的扩展与截断,这部分内容与C语言挂钩.so,我们先看以下C语言的有符号和无符号数.

 

 

C语言中的有符号数和无符号数

有符号数和无符号数的本质区别其实就是采用的编码不同,前者采用补码编码,后者采用无符号编码.

 

C语言中,有符号数和无符号数是可以隐式转换的,不需要手动实施强制类型转换.不过也正是因为如此,可能你一不小心就将一个无符号数赋给了有符号数.就会造成出乎意料的结果,就像下面这样:

#include <stdio.h>

 

int main(){

    short i = -12345;

    unsigned short u = i;

    printf("%d %d\n",i,u);

}

 

你自己观察一下输出结果你就会发现,一个负数变成了正数,再看下面这个程序,他展示了在进行关系运算时,由于有符号数和无符号数的隐式转换所导致的违背常规的结果.

#include <stdio.h>

 

void main(){

    printf("%d\n",-1 < 0U);

    printf("%d\n",-12345 < 12345U);

}

你自己看看输出结果,两个结果都是0,也就是false,这与我们直观的理解是违背的,原因就是因为在比较的过程中,有符号数被隐式的转换成了无符号数进行比较.

 

 

 

扩展

当我们将一个短整型的变量转换为整型变量时,就涉及到了位的扩展,此时由两个字节扩充为四个字节.

 

在进行位的扩展时,最容易想到的就是在高位全部补0,也就是将原来的二进制序列前面加入若干个0,也称为零扩展.还有一种方式比较特别,是符号扩展,也就是针对有符号数的方式,他是直接扩展符号位,也就是将二进制序列的前面加入若干个最高位.

 

对于零扩展来说,很明显扩展之后的值与原来的值是相等的,而对于符号扩展来说,则是一样,只不过没有零扩展来的直观.我们在计算补码时有一个比较简单的办法,就是符号位若为0,则与无符号是类似的.若符号位为1,也就是负数时,可以将其余位取反最终再加1即可.因此当我们对一个有符号的负数进行符号扩展时,前面加入若干个1,在取反之后都为0,因此依旧会保持原有的数值.

 

总之,在对位进行扩展式,是不会改变原有数值的.

 

在书中对于负数的符号扩展还给出了这一过程的证明,其实这个证明很简单,就是利用了补码编码的公式而已.需要多提一点的是,这是使用了归纳法证明,因此这里只是扩展了以为,具体过程如下:

 

 技术分享

 

 

 

 

截断

截断与扩展相反,它是将一个多维二进制序列截断为较少的位数,就是与扩展是相反的过程.

 

根据我们的直观判断也不难发现,截断可能会导致数据的丢失.对于无符号编码来说,截断后就是剩余位数的无符号编码数值.在书中给出了这一简单过程证明,它主要是想表明截断前后的数值的关系是取模所得到的.

 

 

 技术分享

 

对与补码编码来说,截断后的二进制序列与无符号编码是一样的,因此我们只需要多加一步,将无符号编码转换为补码编码就好了.因此对于无符号编码和补码来说,可以得到以下两个公式.

 

 技术分享

 

 

 

其他语言中的有符号和无符号

从上面的分析可以看出,具有有符号和无符号的语言,可能引起一些不必要的麻烦,而且无符号数除了能表示的最大值更大以外,似乎没什么好处了.因此有很多语言是不支持无符号数的.

我接触过的C#JAVA就只有有符号数,这样省去了很多不必要的麻烦.无符号数很多时候只是为了表示一些无数值意义的标识,比如我们的内存地址,此时的无符号数有点类似数据库主键或者说键值对中的键值的概念,仅仅是一个标识而已.

 

小结

 

低位转高位叫扩展,高位转低位叫做截断.

 

 

 

 

版权声明:本文为博主原创文章,未经博主允许不得转载。

C语言的有符号与无符号,二进制整数的扩展与截断

标签:计算机   计算机科学   

原文地址:http://blog.csdn.net/shanyongxu/article/details/47658097

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!