参考 第十三篇:带缓冲的IO( 标准IO库 ) https://www.jianshu.com/p/b54e237b6c62

非缓冲的 IO

非缓冲 IO 是指用户层没有缓冲,通过系统调用直接对磁盘文件进行读写。但是对于内核来说,还是进行了缓存,内核把数据写到内核缓冲区中,当缓冲区溢出的时候再进行实际的IO操作。

函数 open read write lseek close,提供了不带缓冲的IO,这些函数都是用文件描述符。文件描述符是一个非常小的非负整数,是内核用来标识正在进行访问的文件。

  1. ssize_t read(int fd,void *buf,size_t count)

从 fd 标识的文件中一次读取 count 字节的字符到 buf,返回一次读取的字节数,小于等于 count

  1. ssize_t write(int fd,void *buf,size_t count)

从 buf 中一次写 count 字节到 fd 标识的文件中,返回一次写入的字节数,小于等于 count

缓冲 IO(标准 IO)

在用户层建立一个流缓冲区(重要内容),库函数向流缓冲区读写数据,流缓冲区溢出时进行系统调用,即再调用非缓冲的 IO。

标准库提供的缓冲 IO 函数是为了减少 read 和 write 函数调用次数而设计的。因为每次调用 read 和 write 函数系统都会中断并陷入内核,增加了 CPU 的负担。

具体的应用类似于非缓冲 IO 函数,只是文件描述符变成了文件指针,多个缓冲设置,多了些格式化 IO 函数罢了。

fwrite fread gets 是标准 IO。

三大缓冲类型

  1. 全缓冲
  2. 在填满标准 IO 缓冲区后才进行实际 IO 操作。
  3. 行缓冲
  4. 在输入和输出过程中遇到换行符时,执行实际 IO 操作。
  5. 不缓冲
  6. 任何时候的实际读写都是在函数调用时进行,函数调用后结束。

缓冲类型是针对流的,而不是针对具体函数的,切记。

数据流向对比

非缓冲 IO 操作数据流向:
数据----> 内核缓冲区---->磁盘

标准IO操作数据流向:
数据---->流缓冲区---->内核缓冲区---->磁盘