C语言的信息表示

前言

C语言是如今最重要、最流行的编程语言之一,相对于其他程序设计语言,C语言更偏向底层结构化设计,提供对硬件更精准的控制,但也要求使用者更关注指针、位等字节级编程,本文以C语言为载体,研究字节级信息的存储和相关特性,讨论字符串、整数、浮点数的编码方式和相关隐患。不正之处,敬请指教

一、位+上下文

众所周知,现代计算机存储和处理的信息以二进制信号表示,即0和1。计算机内都是以0、1bit串存储信息,区分不同信息的唯一方法是根据解析0、1bit串的上下文。

首先,我们来思考这么个问题:给定一个串0110 0001,代表什么含义呢?

在没有任何上下文的时候,我们直观的猜测这是个数字,将二进制转换为十六进制为0x61,转换为十进制则为97
若进一步假定计算机在读取串0110 0001的上下文是解析ASCII码,则串0110 0001被计算机解释为ASCII码中的字符a。但若设定计算机在读取串0110 0001的上下文是unsigned char掩码,则0110 0001不代表任何含义,假如计算机在读取该串的上下文是引用一个字长为8bit的指针,则0110 0001就代表着地址97

单独的bit串并没有意义,信息是通过位+上下文承载的,相同的位串在不同上下文被解释成不同的信息。

二、表示字符串

C语言中的字符串被编码为以null结尾的字符数组,字符串的每个字符通常以ASCII字符码进行编码。

//"123"存储为:0x31 0x32 0x33 0x00
//二进制表示:0011 0001 0011 0010 0011 0011 0000 0000
char *str1 = "123";
//"abc"存储为:0x61 0x62 0x63 0x00
//二进制表示:0110 0001 0110 0010 0110 0011 0000 0000
char *str2 = "abc";
复制代码

字符串的存储方式是不受字节顺序和字长影响的,因此字符串的可移植性是最好的。

三、表示整数

C语言数字编码体系是真实世界数字体系的近似表示,在某系特性上存在一定的差异。

打个比方,C语言用char类型变量存储[-128,127]共256个整数,在使用如下表达式时:

/*例1*/
char x = -128;
char y = -x;//真实世界y应该是128,但是在C语言中,y还是-128!

/*例2*/
char x = 100,y=30;
char sum = x+y;//真实世界y应该是130,但是在C语言中,y-126复制代码

若对C语言数字编码体系不了解,很容易导致程序出现极其隐秘的bug。下面我们着重讨论C语言是如何表示整数、浮点数。

(一)表示无符号

1. 概述

C语言针对整数提供两种编码方式:无符号编码(unsigned)、有符号编码(signed)。

首先,我们来看一下十进制的正整数表示方式,思考我们如何解释123数字。应该为123=3100+2101+1102123=3*10^0+2*10^1+1*10^2

类比到无符号8bit的二进制0110 0001,有:

01100001=120+125+126=970110 0001=1*2^0 + 1*2^5 + 1*2^6=97

© 版权声明
THE END
喜欢就支持一下吧
点赞0 分享