• 第一章 温故而知新


    一、从Hello World说起

    #include<stdio.h>
    
    int main()
    {
        printf("Hello world
    ");
        return 0;
    }

    1、程序为什么要被编译器编译了之后才可以运行?

    2、编译器在把C语言程序转换成可以执行的机器码的过程中做了什么?怎么做的?

    3、最后编译出来的可执行文件里面是什么?除了机器码还有什么?他们怎么存放的,怎么组织的?

    4、#include<stdio.h>是什么意思?把stdio.h包含进来是意味这什么?C语言库又是什么?他怎么实现的?

    5、不同的编译器和不同的硬件平台以及不同的操作系统,最终编译出来的结果一样吗?为什么?

    6、Hello World程序是怎么运行起来的?操作系统是怎么装载它的?它从哪儿开始执行,到哪儿结束?main函数之前发生了什么?main函数结束以后又发生了什么?

    7、如果没有操作系统,Hello World可以运行吗?如果要在一台没有操作系统的机器上运行Hello World需要什么?应该怎么实现?

    8、printf是怎么实现的?他为什么可以有不定数量的参数?为什么他能够在终端上输出字符串?

    9、Hello World程序运行时,他在内存中是什么样子?

    二、万变不离其踪

    1、北桥芯片主要协调CPU、内存和高速的图形设备;南桥芯片主要协磁盘、USB等低速设备

    2、对称多处理器(SMP:Symmetrical Multi-Processing):简单地讲就是每个CPU在系统中所处的地位和所发挥的功能都是一样的,是相互对称的。

    3、多核处理器(Multi-Core Processer):将多个处理器合并在一起打包出售,这些被打包的处理器之间共享比较昂贵的缓存部件,只保留多个核心,可以视作SMP简化版。

    4、操作系统作用:CPU调度(多道程序-->分时系统-->多任务系统);设备驱动;内存管理(直接使用物理内存-->分段-->分页)

    三、线程基础

      线程(Thread),有时被称为轻量级进程(Lightweight Process, LWP)是程序执行流的最小单元。一个标准的线程是由线程ID、当前指令指针(PC)、寄存器集合和堆栈组成。通常意义上,一个进程是由一个到多个线程组成,各个线程之间共享程序的内存空间(包括代码段、数据段、堆等)及一些进程级的资源(如打开文件和信号)。

    1、多线程使用场景:a、某个操作可能会陷入长时间等候;b、某个操作是CPU密集型;c、程序逻辑是并发(下载);d、相比多进程,多线程共享效率更高

    2、线程的私有空间:a、栈;b、线程局部存储;c、寄存器

    3、线程的共享空间:a、全局变量;b、堆上的数据;c、函数里的静态变量;d、程序代码,任何线程都有权限读取并执行任何代码;e、打开的文件等资源

    4、原子操作:单指令的操作称之为原子操作,因为无论如何,单条指令的执行都不会被打断。为了避免出错,很多体系结构都提供了一些常用的原子指令。

    四、线程安全

      为了避免多个线程同时读写同一个数据而产生不可预料的后果,我们要将各个线程对同一个数据的访问同步(Synchronization)。所谓同步,即指在一个线程访问数据未结束的时候,其他线程不得对同一个数据进行访问。

      常用的线程同步方式:a、二元信号量(Binay Semaphore)/信号量(Semaphore);b、互斥量(Mutex);c、临界区(Critical Section);d、读写锁(Read-Write Lock);e、条件变量(Condition Variable)。

      可重入函数必须满足几个特点:a、不使用任何静态或局部的非const变量;b、不返回任何静态或全局的非const变量的指针;c、仅依赖与调用方提供的参数;d、不依赖任何单个资源的锁;e、不调用任何不可重入的函数。

    五、Double-Check

    volatile T*pInst = 0;
    T* GetInstance()
    {
        if(pInst == NULL)
      {
            lock();
            if(pInst == NULL)
           {
                pInst = new T;
            }
            unlock();
        }
        return pInst;
    }

       上面的代码不是线程安全的,原因有二:1、编译乱序;2、CPU执行乱序

  • 相关阅读:
    使用find命令删除文件的4种方式
    练习题: tail -f/-F & tr命令的使用原理&如何卸载软件& 批量新增用户并设置密码
    vim异常问题说明及工作原理
    系统阶段回顾部门-编辑命令使用技巧-vim
    系统优化操作部分-yum下载源优化
    系统目录结构部分-环境变量和别名配置文件
    E. OpenStreetMap(单调队列)
    E. OpenStreetMap(单调队列)
    线性基
    线性基
  • 原文地址:https://www.cnblogs.com/cauchy007/p/6759760.html
Copyright © 2020-2023  润新知