天天看点

《操作系统真象还原》——0.27 转义字符与ASCII码

本节书摘来自异步社区《操作系统真象还原》一书中的第0章,第0.27节,作者:郑钢著,更多章节内容可以访问云栖社区“异步社区”公众号查看

计算机世界中是以二进制来运行的,无论是指令、数据,都是以二进制的形式提交给硬件处理的,字符也一样,必须转换成二进制才能被计算机识别。所以各种各样的字符编码产生,简单来说,字符编码就是用唯一的一个二进制串表示唯一的一个字符。其中最著名的字符编码就是ascii码。

ascii码表中字符按可见分成两大类,一类是不可见字符,共33个,它们的ascii码值是0~31和127,属于控制字符或通信专用字符。表中其余的字符是可见字符,它们的ascii码值是32~126,属于数字、字母、各种符号。

对于计算机来说,任何字符都是用ascii码表示的,人要是与计算机交流,虽然可以直接输入字符的ascii码,但这太不人道了,计算机的发明是为了给人解决问题而并非制造问题。人习惯用所见即所得的方式使用字符,我要输入字符a的时候,直接按下键盘上的a键就行了,不要让我输入其ascii码0x61。这要求是合理的,我们在键盘上键入的每个按键,都会由输入系统根据ascii码表转换成对应的二进制acsii码形式。这对普通用户来说够用了,他们很少写程序,可是作为程序员,我们经常要输出字符串,字符串中的可见字符直接从键盘敲入就行了,对于那些不可见字符,如回车换行符等,肯定不能用键盘在字符串中直接敲下一个回车键。

我们的问题是不可见字符如何写出来,也就是说我们在写字符串时,如何在其中加入不可见的控制符,这就需要编译器或解释器的支持了。

由于可见字符本身是看得见的,所见即所得,大家在使用中并不会有陌生感。对于那些不可见的控制字符,如果想使用它们时,该怎样表示它们呢?比如我就是要让程序输出一段话,在结束处换行。控制字符看不见摸不着,怎么写出来?所以在使用这些不可见字符时必须想办法让其可见,但又不能表示成其他可见字符,所以,只能让可见字符不表示自身了,哈哈,有点难是吗?这么艰巨的任务显然只用一个可见字符是不可能完成的,于是编译器想出了一个办法,它引用了另一个可见字符''来搭配其他可见字符,用这种可见字符组合的形式表达不可见字符。表面上看,字符''是让其他可见字符的意义变了,所以称''为转义字符,但本质上,这两个可见字符合起来才是完整的不可见字符,比如换行符'n',''和'n'放到一起才是换行符的意义,并不是因为'n'前面有个'','n'就不再是'n',而是换行符,一定要清楚不是这样的。

ascii码表中任何字符都是1个字节大小,在字符串中不可见字符虽然用“转义字符+可见字符”两个字符来表示,但这只是编译器为了让人们能写出不可见字符的方式,目的是让不可见字符变得“可见”,针对的是人,这样人们写程序时就能在字符串中用到不可见字符。不可见字符本身在编译后还是那1个字节的ascii码。说白了,我们能够将不可见字符显示出来,原因就是编译器在给我们做支持,它将“转义字符+可见字符”这种形式的不可见字符转换成了该不可见字符的ascii码。

为了说清楚,咱们以编译器为界限,在编译器左边的是人,这里的字符串是供人使用的,转义字符是存在于这一边的。编译器右边的是机器,这里的字符串使用的都是ascii码。

在编译器左边:

<code>char* ptr=”abc\n”;</code>

此部分对应的内容是0x61 0x62 0x63 0x5c 0x6e。

编译器右边:

“abcn”对应的内容是0x61 0x62 0x63 0xa

编译器的左边和右边是不一样的,区别是对“n”的处理。编译器左边把它当成了两个字符,编译器右边把它当成了一个字符。想想也是,毕竟代码只是文本字符串,字符串”abcn”中的''和'n'肯定是两个字符,编译器会把''和'n'组合到一起成为'n'而解释成回车换行。可能您还是觉得怀疑,那我说一下编译器对字符串的解释过程。

编译器对字符串的处理一般是逐个字符处理的,这样便于处理转义字符。若发现字符为'',就意识到这是转义字符,按常理说后面肯定要跟着另一可见字符,于是先不做任何处理,马上把后面的字符读进来,分析这两个字符的组合是哪个控制字符后一并处理。

咱们这里拿编译器解释字符串”abcn”举例。

代码中的'n'本身由两个字符''和'n'组成,'n'是给人看的,用于在字符串中使用,其ascii码是0xa,是给机器看的。在计算机中,所有的字符都已经成了ascii码,字符串”abcn”则变成了ascii码:0x61 0x62 0x63 0x5c 0x6e。

编译器要逐个对比字符串中每个字符,前几个字符是'a'、'b'、'c',这都是可见字符,没有异议,直接处理。当发现字符是'',知道这是转义字符,得知道''后面的字符是什么才能确定是哪个不可见字符,于是暂停处理'',把后面的字符读进来,发现是'n',便知道这是'n',表示一个换行符,于是将''和'n'用换行符的ascii代替,原来字符串”abcn”的ascii码就变成了0x61 0x62 0x63 0xa。

说得足够多了,我也嫌自己啰嗦了,大家看以下的例子吧,就在图0-20中全部解释清楚了。

代码ascii.c过于简单,纯粹是为演示。大家可能注意到了xxd.sh这个脚本,它就是xxd命令的封装,xxd命令可以逐字节查看文件,xxd.sh脚本内容如下。

《操作系统真象还原》——0.27 转义字符与ASCII码

希望对大家理解转义字符有帮助。

继续阅读