非常规入门C语言:2、初始数据类型

<p>日常生活中,在我们周围充斥着各种各样的数据。这些数据有着不同的形式,且分布在不同的载体上。</p><p>但有些数据是有意义的,如费用余额、学号、身份证号、姓名、年龄等;而有些数据是无意义的,如......</p><p>而计算机被发明以来,天生就是服务于科学计算的,即:<strong>一切计算机问题都是数学问题</strong>。</p><p>在<strong><a>上一章</a></strong>中,计算机底层的计算方式是通过二进制来确定的。同时为了能够方便地使数据参与运算,还引出最小处理宽度(宽度就二进制位数)和控制指令。</p><p>那我们可以把哪些数据放在计算机“里面”呢?</p><p>理论上,所有数据都可以。但首先我们解决数据从哪里来的问题,即信息的数字化。</p><p>首先,和数值相关的东西,我们可以很方便存储在计算机中,剩下的问题就是精度和宽度的问题。</p><p>其次,我们还需要解决非数值信息的数字化问题。</p><p>那么我们先解决哪个问题呢?</p><p>为了避免问题的延伸,我们先解决宽度的问题,即给不同的数据分配一个确定的类型,即数据类型。</p><p>首先,我们能确定的第一个数据类型就是计算机的最小处理宽度,无论是哪种机器,无论它的最小处理宽度是多大,我们都称之为“字”,字的宽度称之为“字宽”。那么为了和二进制搭上关系,我们采用倍数增长的方式,扩大数据类型的表示范围。</p><p>字->双字->四字->八字->16字->32字->64字......</p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-743bbaf5905b9bfe.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/></p><p>你想扩大多少倍都可以,但必须是前一个数值的2倍。因为这样的处理方式的难度是最低的。</p><p>于是,基于“字”概念的数据类型就出现了。但是它本身并不具有通用性和实际意义,因为“无论它的最小处理宽度是多大,我们都称之为‘字’”。</p><p>这时,我们应该想到貌似有一个8位的数据。没错,在<strong><a>上一章</a></strong>中,我们使用8位二进制的数据完整表示了<strong>控制字符</strong>(如换行等)、<strong>大小写字母</strong>、<strong>数字</strong>和<strong>常用标点符号</strong>。那么,干脆就用8位作为最小处理宽度。</p><p>那么,给个名字,把8位宽度的称为“字节”,同时将“字节”确定为通用的基本字宽。</p><p>这时,我们得到了一些较为原始的数据类型:字节、双字节、四字节......</p><p>我们能有多大的数呢。。。这是一个问题。因为需要看CPU能处理多大的数。32位的CPU最大一次性处理32位,64位CPU最大一次性处理64位。为啥是一次性呢?理论上来说,只要你能提供足够的存储空间,数字多大都没问题,但是运算是一部分一部分来的,极端情况也有可能是一位一位来计算的。这种由CPU确定的最大一次性处理宽度,称之为“数据宽度”。</p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-19256a575bed70f0.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/></p><p>早期计算机的数据类型就是这样。。。很枯燥,很直白,但也很简约。</p><p>但这不是我们的目标,我们的目标是“星辰大海”。</p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-19256a575bed70f0.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/></p><p>1 + 1 = 2</p><p>1 - 2 = ?</p><p>当你在计算时有没有想到这样一个问题:正整数可以直接表示,但负整数和小数没办法直接在计算机中表示。</p><p>因为计算机中没有负号和小数点的概念。解决办法也是相当简单粗暴:用正整数来表示不就好了?</p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-19256a575bed70f0.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/></p><p><strong>举个例子</strong>:</p><p>使用字节来控制字宽。那最长就是8位,表示的范围就是0到255(即0000 0000 ~ 1111 1111)。</p><p>首先我们先确定一下正数与负数的交界点,那就是0。那我们就可以确定,0加上1就是正数,0减掉1就是负数。</p><p>如果我们需要表达-2,那就是0000 0000 - 0000 0010就等于1111 1110,因为0减1不足,向前借2。</p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-4305d4839af3ecee.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/></p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-c57ff2caf197d829.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/>那么,教科书里是怎样教的呢?</p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-c57ff2caf197d829.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-fa2ef72ba7aa2442.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/>嬴寒隐约记得,取反码再加1。。其实很简单,根本用不着反码。所谓反码,只是计算机的一种取反运算而已,因为相比加减运算,取反的操作,那简直是太快了,瞬时就可以完成。</p><p>为什么是瞬时呢?因为只需要对前面的位进行取反,最低位根本不用管就可以完成一个负数的完整表达。根本不可能使用加减运算。但作为人类,我们有时有必要理解计算机的运算方式,但有时又没有必要。而像这种特别基础,基础到对后面的知识没有什么太大影响的东西,我们只需要理解最人性化的思路就可以了。</p><p>但是教科书却用计算机运算的方式来介绍负数的表示原理,无疑是给刚接触的小伙伴带来了沉痛的负担。</p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-19256a575bed70f0.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/></p><p>各位小伙伴可能已经发现,在计算机中,处于最高位的0是一个非常神奇的存在。我们通过它能够辨别是正数还是负数,也能够通过它,来判断一个数据是不是正确的(就是低位数据的每一位运算的结果,称为校验)。其实我们还可以利用0来确定真假值,比如0为真,非0为假,我们称之为“布尔值”。</p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-19256a575bed70f0.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/></p><p>刚刚我们找到了负数的表示方案,此时,我们就需要找到非整数的表示方法了。那么如何利用整数来表示非整数呢?</p><p>一种方式是直接规定第多少位开始是小数部分,当然这种方式没人会喜欢,而且灵活性也很差。</p><p>其实这里我们就考虑到了小数点的变动问题:小数点是不动(小数位数固定)还是变化的(小数位数不定)。显然,两种形式各有优劣。</p><p>既然整数的表达最方便,那能否让小数和整数直接挂钩呢?可以。</p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-19256a575bed70f0.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/></p><p>我们以科学计数法再<strong>举个例子</strong>:</p><p>使用二进制表示259.56,如果将其转换为科学计数法就是2.595610^2。</p><p>但很显然我们还是没办法直接表示,既然缩小不行,那就尝试放大。于是我们可到等价的值2595610-2。这时其中所有相关的数值我们都是在计算机方便的表示:25956、10和-2。</p><p>但是不要忘了,计算机是基于二进制的,并非十进制,那就意味着,必须将这仨兄弟都转换成二进制就可以了。</p><p>可是,好像不太容易啊。因为我们一直是按照十进制来处理,但换成二进制中,小数点的变动就不一样了。</p><p>所以我们将259.56拆成两部分,使用常规方案表示整数部分259,使用小数表示法表示小数部分0.56。</p><p>在十进制的世界中,1是1*100,10是110^1,0.1是110-1。</p><p>在二进制中也是基本一致的,1是1*20,2是12^1。</p><p>也就是说,我们需要表达某个大数,就是让这个数除以基数,十进制的基数就是10,那么二进制的基数就是2;反之,如果我们需要表达一个凑不整基数的小数,就需要让这个数乘以基数。</p><p>例如:256就是200+50+6=2100 +510+61,表达逻辑是让原来的数缩小,让基数增大。</p><p>再如:0.25就是0.2+0.05=210^-1+510^-2,表达逻辑是原来的数变大,让基数减小。(说法不是很严谨,因为不是让基数本身发生变化,而是权值,或者说是指数部分)</p><p>那么,0.56表示成二进制就是让这个数一直乘以2,直到小数部分没有值为止。</p><p>0.56 * 2 = 1.12 -> 取 1</p><p>0.12 * 2 = 0.24 -> 取 0</p><p>0.24 * 2 = 0.48 -> 取 0</p><p>0.48 * 2 = 0.96 -> 取 0</p><p>0.96 * 2 = 1.92 -> 取 1</p><p>……</p><p>很长很长:.100 0111 1010 1110 0001 0100 0111 1010 1110 0001 0100 0111 1011</p><p>所以就涉及到精度问题。。。因为我们不可能把所有精力和空间全浪费在小数的处理上。除非。。。有东西能够帮我们自动完成这件事。</p><p>那么,上面的259.56就可以分成三部分了,整数部分、小数部分、小数点位数。</p><p>当然,这只是一个示例。并不一定是现代计算机中用到的表达方式。</p><p class="image-package"><img class="uploaded-img" src="https://upload-images.jianshu.io/upload_images/27354708-19256a575bed70f0.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240" width="auto" height="auto"/></p><p>至此,我们已经利用计算机中原有的东西实现了一些类型,如:数值、字符、布尔值,暂且称他们为“初始数据类型”吧。</p><p>
</p>

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 194,088评论 5 459
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 81,715评论 2 371
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 141,361评论 0 319
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,099评论 1 263
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 60,987评论 4 355
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,063评论 1 272
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,486评论 3 381
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,175评论 0 253
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,440评论 1 290
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,518评论 2 309
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,305评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,190评论 3 312
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,550评论 3 298
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 28,880评论 0 17
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,152评论 1 250
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,451评论 2 341
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,637评论 2 335

推荐阅读更多精彩内容