《Expert C Programming》阅读笔记

  从接触Linux开始,一直学习并使用C语言,C语言与Linux是相辅相成的。从刚开始对C的了解学习到慢慢熟练使用,渐渐认识到C的精妙,C语言比较贴合底层硬件,要求编码时对程序更精确的掌控。

  通过阅读《C专家编程》,对C语言的理解包括编译等都有了更深刻的了解,C强调一切由程序员实现,编码时需要保证自己程序的准确,《C专家编程》给我最有意义的认识是:在编码时更清楚程序的运行细节,从底层硬件及Linux系统函数实现的角度更深入的认识了高质量编码。

  书中通过实例讲解,并给出编程挑战,阅读跟实践相结合,加深了对内容的理解,编程实现的同时让人有茅塞顿开的感觉。下面总结几个印象最深刻的知识点:

  一. 程序运行时的数据结构:

  清楚的了解了可执行程序的各个段(文本段、数据段、bss段),以及其在内存中的布局(如下图)。

  

  1.编译“hello world”程序,在可执行文件中执行ls -l,得到文件的总体大小。运行size得到文件里各个段的大小。

  

  2.增加一个全局的int[1000]数组声明,重新进行编译,再用上面的命令得到总体及各个段的大小。可以清楚看到增加全局的未初始化的int数组,都保存在bss段。

  

  3.现在,在数组的声明中增加初始值(C语言并不强迫对数组进行初始化时为每个元素提供初始值)。可以看到初始化全局数组后,使数组从BSS段转换到数据段。

  

  4.在函数内声明一个巨大的数组。然后再声明一个巨大的局部数组,最后在加入一个函数,并在函数内部声明一个大数组。可以看到后面增加的局部大数组声明都布局在文本段。

  

二.对内存的思考

  阅读此章节后,对Intelx86的内存工作原理以及MMU都有了进一步的理解,并对linux本身的系统函数实现及贴合硬件的优化进行了学习和了解(例如提到的memcpy函数的优化实现),总结一下印象比较深的几个知识点:

  1.虚拟内存

  a.虚拟内存 – 使用磁盘保存运行进程的映像,通过“页”的形式组织,页就是磁盘和内存之间来回移动的单位

  b.在磁盘上有个特殊的交换区,用来保存从内存中换出的进程

  c.进程只能操作位于物理内存中的页面

  2.Cache

  a.Cache的操作速度域系统的周期时间相同

  b.Cache包含一个地址的列表以及它们的内容,所有对内存的读取和写入都要经过cache

  c.Cache采用写直达,写回法,保持命中

  d.行Line是对Cache进行访问的单位,一个行内的数据成为块block

  3.堆和数据段

  a.堆中的所有东西都是匿名的,不能按名字访问,只能通过指针

  b.堆内存的回收不必与所分配顺序一致,它甚至可以不回收

  c.管理内存的调用:malloc、free、brk和sbrk(调整数据段的大小)

  4.内存泄漏

  a.堆经常出现两种类型的问题

  b.释放和改写仍在使用的内存(内存损坏)

  c.未释放不再使用的内存(内存泄漏)

  每次malloc后,调用free释放它。或者,尽可能地使用alloca来分配,它会被自动释放掉。

  5.总线错误

  a.总线错误计划局都是由于未对齐的读和写引起的,而数据项是不能跨越页面或Cache边界的

  b.编译器通过自动分配和填充数据来进行对齐

  以上是自己在阅读笔记中总结的印象比较深刻的两个点,看《C专家编程》的同时,实例编码调试,从不同的角度、深度去理解了C编程的奥妙,还是比较有成就感的。书中很多有趣的IT历史事件,项目实例等也让我获益匪浅,总之,即使多了点滴认识,也是很愉快的:)。

posted @ 2014-05-11 21:56  andyzhekun  阅读(416)  评论(0编辑  收藏  举报