# 导言:C的笛卡尔之梦
> 原文:[Introduction: The Cartesian Dream Of C](http://c.learncodethehardway.org/book/introduction.html)
> 译者:[飞龙](https://github.com/wizardforcel)
‍
> 直到现在,凡是我当作最真实、最可靠而接受的东西,都是从感官或通过感官得来的。不过,我有时觉得这些感官是骗人的,并且为了小心谨慎起见,对于一经骗过我们的东西就决不完全加以信任。
> 勒内·笛卡尔,《第一哲学沉思录》
如果有一段引述用来描述C语言编程的话,那就是它了。对于大多数程序员,C是极其可怕而且邪恶的。他就像是恶魔、撒旦,或者一个使用指针的花言巧语和对机器的直接访问来破坏你生产力的骗子洛基。于是,一旦这位计算界的路西法将你缠住,他就会使用邪恶的“段错误”来毁掉你的世界,并且揭露出与你交易中的骗局而嘲笑你。
然而,C并不应由于这些事实而受到责备。你的电脑和控制它的操作系统才是真正的骗子,而不是朋友。它们通过密谋来向你隐藏它们的真实执行逻辑,使你永远都不真正知道背后发生了什么。C编程语言的失败之处只是向你提供接触背后真正工作原理的途径,并且告诉了你一些难以接受的事实。C会向你展示痛苦的真像(红色药丸),它将幕布拉开来向你展示一些神奇的原理。C即是真理。
既然C如此危险,为什么还要使用它?因为C给了你力量来穿越抽象的假象,并且将你从愚昧中解放出来。
## 你会学到什么
这本书的目的是让你足够熟悉C语言,并能够使用它编写自己的软件,或者修改其他人的代码。这本书的最后,我们会从一本叫做“K&R C”的名著中选取实际的代码,并且用你学过的知识来做代码审查。你需要学习下面这些东西来达到这一阶段:
+ C的基本语法和编写习惯。
+ 编译,`make`文件和链接。
+ 寻找和预防bug。
+ 防御性编程实践。
+ 使C的代码崩溃。
+ 编写基本的Unix系统软件。
截至最后一章,你将会有足够的工具来解决基本的系统软件、库和其它小项目。
## 如何阅读本书
这本书为那些已经掌握至少一门编程语言的人而设计。如果你还没有接触过编程,我推荐你先学习[笨办法学Python](http://learnpythonthehardway.org/),这本书适用于真正的新手并且适合作为第一本编程书。一旦你学会了Python,你可以返回来开始学习这本书。
对于那些已经学会编程的人,这本书的开头可能有些奇怪。它不像其它书一样,那些书中你会阅读一段段的文字然后编写一些代码。相反,这本书中我会让你立即开始编程,之后我会解释你做了什么。这样更有效果,因为你已经经历过的事情解释起来更加容易。
由于采用了这样的结构,下面是本书中你必须遵守的规则:
+ 手动输入所有代码。不要复制粘贴!
+ 正确地输入所有代码,也包括注释。
+ 运行代码并保证产生相同的输出。
+ 如果出现了bug则修正它。
+ 做附加题时,如果你做不出某道题,马上跳过。
+ 在寻求帮助之前首先试着自己弄懂。
如果你遵守了这些规则,完成了本书的每一件事,并且还不会编程C代码的话,你至少尝试过了。它并不适用于每个人,但是尝试的过程会让你成为一个更好的程序员。
## 核心能力
我假设你之前使用为“弱者”设计的语言。这些“易用的”语言之一是Python或者Ruby,它们带给了你草率的思维和半吊子的黑魔法。或者,你可能使用类似Lisp的语言,它假设计算机是纯函数式的奇幻大陆,带有一些为婴儿准备的充气墙。再或者你可能学过Prolog,于是你认为整个世界都是一个数据库,你可以从中寻找线索。甚至更糟糕的是,我假设你一直都在用IDE,所以你的大脑布满了内存漏洞,并且你每打三个字符都要按CTRL+空格来打出函数的整个名字。
无论你的背景如何,你都可能不擅长下面四个技能:
阅读和编写
如果你使用IDE这会尤其正确。但是总体上我发现程序员做了很多“略读”,并且在理解上存在问题。它们会略读需要详细理解的代码,并且觉得他们已经理解了但事实上没有。其它语言提供了可以让他们避免实际编写任何代码的工具,所以面对一种类似C的语言时,他们就玩完了。你需要知道每个人都有这个问题,并且你可以通过强迫自己慢下来并且仔细对待阅读和编写代码来改正它。一开始你可能感到痛苦和无聊,但是这样的次数多了它也就变得容易了。
专注细节
每个人都不擅长这方面,它也是劣质软件的罪魁祸首。其它语言让你不会集中注意力,但是C要求你集中全部注意力,因为它直接在机器上运行,并且机器比较挑剔。C中没有“相似的类型”或者“足够接近”,所以你需要注意,再三检查你的代码,并假设你写的任何代码都是错的,直到你能证明它是对的。
定位差异
其它语言程序员的一个关键问题就是他们的大脑被训练来指出那个语言的差异,而不是C。当你对比你的代码和我练习中的代码时,你的眼睛会跳过你认为不重要或者不熟悉的字符。我会给你一些策略来强制你观察你的错误,但是要记住如果你的代码并不完全像书中的代码,它就是错的。
规划和调试
我喜欢其它较简单的语言,因为我可以想怎么写就怎么写。我将已有的想法输入进解释器,然后可以立即看到结果。你可以把你的想法试验出来,但是要注意,如果你仍然打算“试验代码使其能够工作”,它就行不通了。C对于你来说稍困难,因为你需要规划好首先创建什么。的确,你也可以进行试验,但是比起其他语言,你必须在C中更早地严肃对待代码。我会教给你在编程之前规划程序核心部分的方法,这对于使你成为更好的程序员十分有帮助。即使一个很小的规划,都会使接下来的事情变得顺利。
学习C语言会使你变成更好的程序员,因为会强制你更早、更频繁地解决这些问题。你不会再草率地编写半吊子的代码,代码也会能够正常工作。C的优势是,它是一个简单的语言,你可以自己来弄清楚,这使得它成为用于学习机器,以及提升程序员核心技能的最佳语言。
C比其它语言都要难,而这是由于C并不对你隐藏细节,它们在其它语言中都试图并且未能被掩盖。
## 协议
原书在完稿之后可以自由分发,并且能在[亚马逊](http://www.amazon.com/Learn-Hard-Way-Practical-Computational/dp/0321884922/)上购买。该中译版本遵循[CC BY-NC-SA 4.0](http://creativecommons.org/licenses/by-nc-sa/4.0/)协议,你可以在保留署名和出处的前提下以非商业目的自由转载。
- 笨办法学C 中文版
- 前言
- 导言:C的笛卡尔之梦
- 练习0:准备
- 练习1:启用编译器
- 练习2:用Make来代替Python
- 练习3:格式化输出
- 练习4:Valgrind 介绍
- 练习5:一个C程序的结构
- 练习6:变量类型
- 练习7:更多变量和一些算术
- 练习8:大小和数组
- 练习9:数组和字符串
- 练习10:字符串数组和循环
- 练习11:While循环和布尔表达式
- 练习12:If,Else If,Else
- 练习13:Switch语句
- 练习14:编写并使用函数
- 练习15:指针,可怕的指针
- 练习16:结构体和指向它们的指针
- 练习17:堆和栈的内存分配
- 练习18:函数指针
- 练习19:一个简单的对象系统
- 练习20:Zed的强大的调试宏
- 练习21:高级数据类型和控制结构
- 练习22:栈、作用域和全局
- 练习23:认识达夫设备
- 练习24:输入输出和文件
- 练习25:变参函数
- 练习26:编写第一个真正的程序
- 练习27:创造性和防御性编程
- 练习28:Makefile 进阶
- 练习29:库和链接
- 练习30:自动化测试
- 练习31:代码调试
- 练习32:双向链表
- 练习33:链表算法
- 练习34:动态数组
- 练习35:排序和搜索
- 练习36:更安全的字符串
- 练习37:哈希表
- 练习38:哈希算法
- 练习39:字符串算法
- 练习40:二叉搜索树
- 练习41:将 Cachegrind 和 Callgrind 用于性能调优
- 练习42:栈和队列
- 练习43:一个简单的统计引擎
- 练习44:环形缓冲区
- 练习45:一个简单的TCP/IP客户端
- 练习46:三叉搜索树
- 练习47:一个快速的URL路由
- 后记:“解构 K&R C” 已死
- 捐赠名单