import{_ as l,c as i,o as s,a6 as a}from"./chunks/framework.CZRoMP2i.js";const e="/c/assets/1.D4a42fT1.jpg",t="/c/assets/2.D2wnxl5F.png",n="/c/assets/3.Dq625oo9.jpg",o="/c/assets/4.uqu1DEK4.png",c="/c/assets/5.C6Q0Q8kf.jpg",d="/c/assets/6.B4Srsb-0.png",p="/c/assets/7._D_c8Lrn.png",r="/c/assets/8.DlIyFGDg.png",h="/c/assets/9.7zkUmpQw.png",u="/c/assets/10.h1ugtjyX.png",k="/c/assets/11.D5PWTabw.png",b="/c/assets/12.Bvs6QYjl.jpg",C="/c/assets/9.7zkUmpQw.png",g="/c/assets/14.CsR5exrN.png",m="/c/assets/15.BRG9GQdT.png",E="/c/assets/16.C2sciGZn.png",y="/c/assets/17.DdyXXyxJ.png",v="/c/assets/18.DIeb_KXW.png",A="/c/assets/19.C-kvMz2p.png",x="/c/assets/20.CQqFxmDa.png",_="/c/assets/21.CjMWyIiX.png",f="/c/assets/22.DFQhcDgs.png",P="/c/assets/23.Cco1vsW8.png",L=JSON.parse('{"title":"第一章:计算机组成原理","description":"","frontmatter":{},"headers":[],"relativePath":"notes/01_c-basic/00_xdx/index.md","filePath":"notes/01_c-basic/00_xdx/index.md","lastUpdated":1724099162000}'),S={name:"notes/01_c-basic/00_xdx/index.md"},T=a('

IMPORTANT

NOTE

总结就是一句话:C 语言重要(赞),很重要(大赞),非常重要(非常赞),绝对重要(无敌赞),史无前例的重要(一赞到底)!!!

第一章:计算机组成原理

1.1 计算机系统

1.2 冯·诺依曼体系结构

IMPORTANT

冯·诺依曼体系结构是现代计算机(量子计算机除外)设计的基础

NOTE

上述的组件协同工作,构成了一个完整的计算机系统:

1.3 各种硬件处理速度和性能优化

img

img

txt
1 秒 = 1000 毫秒,即 1 s = 1000 ms。
1 毫秒 = 1000 微妙,即 1 ms = 1000 us 。
1 微妙 = 1000 纳秒,即 1 us = 1000 ns。
txt
如果 CPU 的时钟周期按照 1 秒计算,
那么,内存访问就需要 6 分钟;
那么,固态硬盘就需要 2-6 天;
那么,传统硬盘就需要 1-12 个月;
那么,网络访问就需要 4 年以上。
txt
鹤寿千岁,以极其游,蜉蝣朝生而暮死,尽其乐,盖其旦暮为期,远不过三日尔。
	                                        --- 出自 西汉淮南王刘安《淮南子》
txt
寄蜉蝣于天地,渺沧海之一粟。 哀吾生之须臾,羡长江之无穷。 
挟飞仙以遨游,抱明月而长终。 知不可乎骤得,托遗响于悲风。
	                                        --- 出自 苏轼《赤壁赋》

NOTE

对于蜉蝣来说,从早到晚就是一生;而对于我们人类而言,却仅仅只是一天。

img

NOTE

上图以层次化的方式,展示了价格信息,揭示了一个真理,即:鱼和熊掌不可兼得。

IMPORTANT

CPU 都是直接和内存打交道的,即:CPU 会直接从内存中读取数据,待数据处理完毕之后,会将结果再次写入到内存中;如果需要将数据持久化(永久)保存(内存是易失性存储器,内存中的数据是以电荷形式存储在存储单元中的。当计算机关闭或断电时,这些电荷很快消散,导致存储在内存中的数据丢失),那么就需要将内存中的数据再刷新到磁盘或硬盘上,即:落盘。

1.4 计算机软件

1.4.1 操作系统的来源

1.4.2 用户态和内核态

类型内核态(Kernel Mode)用户态(User Mode)
权限内核态是操作系统代码运行的模式,拥有访问系统全部资源和执行硬件操作的最高权限。在这种模式下,操作系统的核心部分可以直接访问内存、硬件设备控制、管理文件系统和网络通信等。用户态是普通应用程序运行的模式,具有较低的系统资源访问权限。在用户态,程序不能直接执行硬件操作,必须通过操作系统提供的接口(即系统调用)来请求服务。
安全性由于内核态具有如此高的权限,因此只有可信的、经过严格审查的操作系统核心组件才被允许在此模式下运行。这样可以保护系统不被恶意软件破坏。用户态为系统提供了一层保护,确保用户程序不能直接访问关键的系统资源,防止系统崩溃和数据泄露。
功能内核态提供了系统调用的接口,允许用户态程序安全地请求使用操作系统提供的服务,比如:文件操作、网络通信、内存管理等。用户态保证了操作系统的稳定性和安全性,同时也使得多个程序可以在相互隔离的环境中同时运行,避免相互干扰。

NOTE

java
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.List;

public class Demo {
    public static void writeFile(String filePath, String content) {
        Path path = Paths.get(filePath);
        try {
            Files.write(path, content.getBytes());
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    public static void main(String[] args){
        int a = 10;                                 // 用户态
        int b = 20;                                 // 用户态
        int c = a + b;                              // 用户态
        string filePath = "c:/demo.txt";            // 用户态
        string txt = a + b + c;                     // 用户态
        
        writeFile(filePath, a);                     // 从用户态切换到内核态完成文件写入
        
        System.out.println(a);                      // 从内核态切换回用户态
        System.out.println(b);                      // 用户态
        System.out.println(c);                      // 用户态
    }
}

1.4.3 ISA、ABI 和 API

NOTE

NOTE

NOTE

1.4.4 系统调用(System Call)和函数库(Library Call)

类型系统调用(System Call)函数库(Library Call)
定义系统调用是操作系统提供给程序员的一组接口,这些接口允许用户空间的程序请求操作系统内核提供的服务,比如文件操作、进程控制、通信和内存管理等。函数库调用是指使用高级语言编写的一组预先编译好的函数,这些函数实现了一些常用的功能,比如:字符串处理、数学计算等。程序员可以在自己的程序中直接调用这些函数,而无需重新实现它们。
权限执行系统调用时,会从用户态切换到内核态。这是因为系统调用涉及到访问受保护的系统资源,这些操作必须由操作系统控制以确保系统的稳定性和安全性。函数库调用通常在用户态执行,不涉及到用户态与内核态之间的切换。它们直接使用操作系统通过系统调用提供的服务,或者完全在用户空间内完成计算,不需要操作系统介入。
性能开销由于涉及到用户态与内核态之间的切换,系统调用的执行成本相对较高。因此,频繁的系统调用可能会影响程序的性能。相对于系统调用,函数库调用的性能开销较小。因为它们通常不涉及到模式切换,且执行的操作多在用户空间完成。
示例open(),read(),write(),fork(),exec() 等 UNIX/Linux 系统调用。C 标准库中的 printf() 等函数;数学库中的 sin(),cos() 等函数。

NOTE

第二章:初识计算机语言

2.1 计算机语言是什么?

NOTE

NOTE

2.2 为什么要学习计算机语言?

c
#include <stdio.h> // 这是编译预处理指令

int main() { // 定义主函数

    printf("你好,世界!!!"); // 输出所指定的一行信息

    return 0;  // 函数执行完毕时返回函数值0
}

NOTE

编译器就是运行在操作系统之上的程序,其作用就是用来将程序员编写的源代码转换为计算机能够识别的二进制指令。

NOTE

总结:无论我们学习任何一门编程语言,想要将程序运行起来,都必须做如下的两件事情:

2.3 计算机语言简史

2.3.1 机器语言(相当于人类的石器时代)

txt
0000,0000,000000010000 代表 LOAD A, 16
0000,0001,000000000001 代表 LOAD B, 1
0001,0001,000000010000 代表 STORE B, 16

WARNING

2.3.2 汇编语言(相当于人类的青铜&铁器时代)

WARNING

2.3.3 高级语言(相当于人类的信息时代)

NOTE

IMPORTANT

C 语言出现的时候,已经度过了编程语言的拓荒年代,具备了现代编程语言的特性,但是这个时候还没有出现“软件危机”,人们没有动力去开发更加高级的语言,所以也没有太复杂的编程思想;而之后出现的“面向对象”的编程思想解决了一部分在“软件危机”上的窘境。

2.3.4 总结

类别特征优点缺点示例
机器语言直接由计算机执行的二进制代码执行速度快编写困难,可读性差,与具体硬件强绑定二进制代码
汇编语言用助记符代替二进制代码的低级语言相对机器语言更易编写和理解,允许直接控制硬件资源依然需要了解硬件,不够抽象,与具体硬件或平台相关MOV,ADD 等助记符
高级语言接近人类语言,提供了更高层次的抽象易于编写和维护,可移植性好,支持多种编程范式需要通过编译器或解释器转换为机器语言,可能存在一定的性能损失C,Java, Python 等

IMPORTANT

第三章:初识 C 语言

3.1 C 语言究竟是一门怎样的编程语言?

NOTE

许多著名编程语言的创造者和计算机科学领域的大佬都有学习和使用过 C 语言,如:詹姆斯·高斯林(James Gosling,Java 之父),比雅尼·斯特劳斯特鲁普(Bjarne Stroustrup,C++ 之父),吉多·范罗苏姆(Guido van Rossum,Python 之父),林纳斯·托瓦兹(Linus Torvalds,Linux 之父)等。

IMPORTANT

这些底层知识,包括不限于:数据结构和算法、计算机组成原理、操作系统、计算机网络、设计模式以及编译原理(了解即可):

NOTE

很多人之所以觉得 C 语言难,就是因为栽倒在 C 语言的指针那边(相对比其他的现代化编程语言而言,C 语言的指针确实足够底层和麻烦,需要掌握的细节很多);但是,一旦有所突破,学习之路就会一马平川。

3.2 C 语言的由来

NOTE

C 语言最初是作为 Unix 系统的开发工具而发明的,它的初衷非常简单,就是被设计成一种非常高效的、可以操作硬件的系统级编程语言,然后帮助团队开发 Unix 操作系统。

3.3 为什么要学习 C 语言?

NOTE

NOTE

3.4 计算机语言排行榜

3.5 C 语言到底能做什么?

3.5.1 概述

专用型编程语言描述
SQL专门用于数据库查询和管理,尽管可以嵌入其他编程语言中,但其主要应用是数据库操作。
R主要用于统计分析和数据可视化,广泛应用于数据科学和研究领域。
MATLAB主要用于数值计算、算法开发和数据可视化,广泛应用于工程和科学领域。
VHDL/Verilog用于硬件描述和数字电路设计,主要应用于电子工程领域。
通用型编程语言描述
Python广泛应用于Web开发、数据科学、自动化脚本、人工智能等。
Java用于企业级应用、移动应用开发(Android)、Web 开发等。
C++可用于系统编程、游戏开发、嵌入式系统等多个领域。
JavaScript最初用于 Web 前端开发,现在也广泛用于服务器端(Node.js)、桌面应用开发(Electron)等。

NOTE

C 语言是一门通用型的编程语言,并没有针对某个领域进行优化。但是,C 语言也有很多常见的应用领域。

3.5.2 C 语言的常见应用领域

IMPORTANT

虽然 C 语言的开发场景貌似看起来很多;但是,使用 C 语言的场景几乎就是:底层/系统开发 + 关键组件/模块的开发 + 贴近硬件的开发,这些开发场景非常关注运行效率,或者响应时间,或者硬件资源。

3.6 不学 C 语言,行吗?

NOTE

IMPORTANT

3.7 C 语言的版本选择

3.7.1 概述

3.7.2 版本 1(K&R C)

NOTE

由于 C 语言还没有成文的语法标准,这本书就成了公认标准,以两位作者的姓氏首字母作为版本简称 “K&R C”。

3.7.3 版本 2(ANSI C,又称 C89 或 C90)

NOTE

目前常用的编译器,如:MSVC(Microsoft Visual C++)、GCC、LLVM Clang 等,都能很好地支持 ANSI C 的内容。

3.7.4 版本 3(C99)

NOTE

这个时候的 C 语言编译器基本已经成熟,各个组织对 C99 的支持所表现出来的兴趣不同:

最终导致不同的编译器在部分语法上存在差异。典型的例子就是:ANSI C 规定,只能用常量表示数组的长度,而 C99 取消了这个限制,数组的长度也可以用变量表示(可变长度数组)。对于 C99 的这个新改动,GCC 和 Clang 是支持的,而 MSVC 却不支持。

3.7.5 版本 4(C11)

NOTE

3.7.6 版本 5(C17)

3.7.7 版本 6(C23)

第四章:C 语言的学习技巧

4.1 如何学习 C 语言?

IMPORTANT

IMPORTANT

现代化的高级编程语言的流行程度,除了和编程语言的设计是否优秀有关,最主要的原因就是生态

遗憾的是,C 语言的标准库非常简单,只有输入输出文件操作日期时间字符串处理内存管理,对于网络编程GUI数据库并发需要大量的第三方库操作系统的功能来扩展 C 语言的功能(Java 语言、Go 语言等其他的现代化高级编程语言,都是直接将这些常见的开发场景内置到标准库中,开箱即用,极大的降低了软件开发的难度)。C 语言的第三方库也不是很多(和其它现代化高级编程语言相比,并且大多数的第三方库都是底层库,支持应用开发的库寥寥无几,只有一个 GTK 库能够开发出桌面软件来,而没有与网站开发和 APP 开发相关的库),社区也不是很活跃(和其它现代化高级编程语言相比),更别提缺少自己的包管理器。

IMPORTANT

IMPORTANT

不过,现在 C 语言社区也开始诞生了一些包管理器,如:Conan 和 vcpkg ;也有自己的项目构建工具,如:cmake 、xmake 等。

NOTE

JavaScript 的作者 Brendan Eich(布兰登·艾奇) 曾经这么说:“与其说我爱 JavaScript,不如说我恨它。它是 C 语言和 Self 语言一夜情的产物(致敬 C 语言)。十八世纪英国文学家约翰逊博士说得好:"它的优秀之处并非原创,它的原创之处并不优秀。"”

4.2 项目构建工具和包管理器

4.2.1 概述

4.2.2 项目构建工具

4.2.3 包管理器

4.2.3 注意事项

NOTE

4.3 C 语言为什么没有应用层开发的库?

第五章:附录

5.1 嵌入式领域中的 C 语言

5.1.1 概述

5.1.2 C51(8051 系列微控制器)

NOTE

总结:C51 微控制器适用于资源受限、需要低成本的简单控制系统,非常适合使用 C 语言来进行开发!!!

5.1.3 STM32(STM32 系列微控制器)

NOTE

总结:STM32 微控制器在物联网、消费电子、医疗设备和工业控制等领域表现出色,非常适合使用 C 语言来进行开发,因为 C 语言允许直接进行硬件控制并支持复杂的应用开发。

5.1.3 ARM 架构(特别是 ARM Cortex 系列)

NOTE

总结:ARM Cortex 系列适用于从实时系统到高级嵌入式操作系统的各类应用,支持从低功耗控制到高性能计算的多种需求,非常适合使用 C 语言来进行开发,因为 C 语言不仅用于控制硬件,还广泛应用于操作系统和应用程序的开发。

5.2 C 和 C++ 的关系

NOTE

C++ 是 C 语言的继承者和扩展,它保留了 C 语言的优势,并引入了更多现代编程语言的特性,使得它在更广泛的应用领域中得到应用。

',203),q=[T];function F(D,B,M,I,R,N){return s(),i("div",null,q)}const w=l(S,[["render",F]]);export{L as __pageData,w as default};