A)缓冲区机制

根据应用程序对文件的访问方式,即是否存在缓冲区,对文件的访问可以分为带缓冲区的操作和非缓冲区的文件操作:

a)带缓冲区文件操作:高级标准文件I/O操作,将会在用户空间中自动为正在使用的文件开辟内存缓冲区。

b)非缓冲区文件操作:低级文件I/O操作,读写文件时,不会开辟对文件操作的缓冲区,直接通过系统调用对磁盘进行操作(读、写等),当然用于可以在自己的程序中为每个文件设定缓冲区。

两种文件操作的解释和比较:

1、非缓冲的文件操作访问方式,每次对文件进行一次读写操作时,都需要使用读写系统调用来处理此操作,即需要执行一次系统调用,执行一次系统调用将涉及到CPU状态的切换,即从用户空间切换到内核空间,实现进程上下文的切换,这将损耗一定的CPU时间,频繁的磁盘访问对程序的执行效率造成很大的影响。

2、ANSI标准C库函数 是建立在底层的系统调用之上,即C函数库文件访问函数的实现中使用了低级文件I/O系统调用,ANSI标准C库中的文件处理函数为了减少使用系统调用的次数,提高效率,采用缓冲机制,这样,可以在磁盘文件进行操作时,可以一次从文件中读出大量的数据到缓冲区中,以后对这部分的访问就不需要再使用系统调用了,即需要少量的CPU状态切换,提高了效率。

B)缓冲类型

标准I/O提供了3种类型的缓冲区。

1、全缓冲区:这种缓冲方式要求填满整个缓冲区后才进行I/O系统调用操作。对于磁盘文件的操作通常使用全缓冲的方式访问。第一次执行I/O操作时,ANSI标准的文件管理函数通过调用malloc函数获得需要使用的缓冲区,默认大小为8192。

//come from /usr/include/stdio.h

/* Default buffer size. */

#ifndef BUFSIZ

# define BUFSIZ _IO_BUFSIZ        //BUFSIZ 全局宏定义

#endif

//come from /usr/include/libio.h

#define _IO_BUFSIZ _G_BUFSIZ

//come from /usr/include/_g_config.h

#define _G_BUFSIZ 8192        //真实大小

2、行缓冲区:在这种情况下,当在输入和输出中遇到换行符时,标准I/O库函数将会执行系统调用操作。当所操作的流涉及一个终端时(例如标准输入和标准输出),使用行缓冲方式。因为标准I/O库每行的缓冲区长度是固定的,所以只要填满了缓冲区,即使还没有遇到换行符,也会执行I/O系统调用操作,默认行缓冲区的大小为1024。

下面的两个程序的对比可以得出行缓冲的大小:

3、无缓冲区:

无缓冲区是指标准I/O库不对字符进行缓存,直接调用系统调用。标准出错流stderr通常是不带缓冲区的,这使得出错信息能够尽快地显示出来。

注:①标准输入和标准输出设备:当且仅当不涉及交互作用设备时,标准输入流和标准输出流才是全缓冲的。②标准错误输出设备:标准出错绝不会是全缓冲方式的。

对于任何一个给定的流,可以调用setbuf()和setvbuf()函数更改其缓冲区类型。

1、setbuf

此函数第一个参数为要操作的流对象,第二个参数buf 必须指向一个长度BUFSIZ 的缓冲区。如果将buf 设置为NULL,则关闭缓冲区。如果执行成功,将返回0,否则返回非0 值。

2、setvbuf

此函数第一个参数为要操作的流对象;第二个参数buf 必须指向一个长为BUFSIZ 的缓冲区;第三个参数为缓冲区类型,分别定义如下:

//come from /usr/include/stdio.h

/* The possibilities for the third argument to 'setvbuf'. */

#define _IOFBF 0 /* Fully buffered.*/        //全缓冲

#define _IOLBF 1 /* Line buffered. */        //行缓冲

#define _IONBF 2 /* No buffering. */        //无缓冲

第四个参数为该buf的大小。如果指定一个不带缓冲区的流,则忽略buf和size参数。

如果指定全缓冲区或行缓冲区,则buf 和size 可选择地指定一个缓冲区及其长度。如果出现指定该流是带缓冲区的,而buf 是NULL,则标准I/O 库将自动为该流分配适当长度的缓冲,适当长度指的即是由文件属性数据结构(struct stat)的成员st_blksize 所指定的值,如果系统不能为该流决定此值(例如若此流涉及一个设备或一个管道),则分配长度BUFSIZ 的缓冲区。

此函数如果执行成功,将返回0,否则返回非0 值。

以下是一个修改 buf 大小写文件的实例程序。其源代码如下:

#include < stdio.h>

#include < stdlib.h>

int main()

{

int i;

FILE *fp;

char msg1[] = "hello,world\n";

char msg2[] = "hello/nworld\n";

char buf[128];

/*打开(或者创建)一个文件,然后使用setbuf设置为nobuf情况,并检查关闭前流的情况*/

if((fp = fopen("no_buf1.txt","w")) == NULL)

{

perror("file open fail");

exit(-1);

}

setbuf(fp,NULL);

fwrite(msg1,7,1,fp);

printf("test setbuf(no buf)!check no_buf1.txt\n");//查看 buf 情况

&nbnbsp;    printf("press enter to continue!\n");

getchar();

fclose(fp);//关闭流,因此将回写 buf(如果有 buf 的话)

/*打开(或者创建)一个文件,然后使用 setvbuf 设置为 nobuf 情况,并检查关闭前流的情况*/

if((fp = fopen("no_buf2.txt","w")) == NULL)

{

perror("file open failure!");

exit(-1);

}

setvbuf(fp,NULL,_IONBF,0);         //设置为无 buf

fwrite(msg1,7,1,fp);

printf("test setbuf(no buf)!check no_buf1.txt\n");        //查看 buf 情况

printf("press enter to continue!\n");

getchar();

fclose(fp);//关闭流,因此将回写 buf ( 如果有 buf 的话)

if((fp = fopen("1_buf.txt","w")) == NULL)

{

perror("fail open file");

exit(-1);

}

setvbuf(fp,buf,_IOLBF,sizeof(buf));        //设置为行 buf

fwrite(msg2,sizeof(msg2),1,fp);        //写内容

printf("test setvbuf(line buf)!check 1_buf.txt,because line buf,only data before enter send to file\n");        //查看 buf 情况

printf("press enter to continue!\n");

getchar();

fclose(fp);        //关闭流,因此将回写 buf

//打开(或者创建)一个文件,然后使用 setvbuf 设置为全 buf情况,并检查关闭前流的情况

if((fp = fopen("f_buf.txt","w")) == NULL)

{

perror("file open failure!");

exit(-1);

}

setvbuf(fp,buf,_IOFBF,sizeof(buf));

for(i = 0;i < 2;i++)

{

fputs(msg1,fp);

}

printf("test setbuf(full buf)! check f_buf.txt\n");

printf("press enter to continue!\n");

getchar();

fclose(fp);//关闭流,因此将回写 buf

return 0;

}

其编译过程及运行结果如下:

编译:

运行:

以下内容是在过程中查看各文件内容信息:

[njs@njs]#cat no_buf1.txt

hello,w //写入的7 个字符全部写入到文件中

[njs@njs]#cat no_buf2.txt

hello,w //写入的7 个字符全部写入到文件中

[njs@njs]#cat l_buf.txt

hello //只有回车前的字符写入

[njs@njs]#cat f_buf.txt //没有任何内容写入

运行过程完成后:

[njs@njs]#cat no_buf1.txt

hello,w //与原来内容一样

[njs@njs]#cat no_buf2.txt

hello,w //与原来内容一样

[njs@njs]#cat l_buf.txt

hello

world //因为调用了fclose()函数,刷新了缓冲区,将world 写入

[njs@njs]#cat f_buf.txt

&nbspnbsp;  hello

world //因为调用了fclose()函数,刷新了缓冲区,将hello/nworld 都写入

linux文件缓冲大小,Linux文件缓冲区详解相关推荐

  1. linux 日志按大小切割_nginx入门详解(六)- 日志切割

    上一章讲解了nginx的目录加密功能,本章重点介绍nginx的日志切割. 笨办法学linux:nginx入门详解(五)- 目录加密​zhuanlan.zhihu.com 在第二章,我们探讨了nginx ...

  2. 过滤Linux下不同大小的文件,linux查找当前目录下 M/G 大小的文件,删除Linux下指定大小的文件

    过滤Linux下不同大小的文件,linux查找当前目录下 M/G 大小的文件,删除Linux下指定大小的文件 find ./ -type f -size +1G| xargs rm 在清理系统日志文件 ...

  3. linux df 目录大小,Linux命令du df查看文件和文件夹大小

    当磁盘大小超过标准时会有报警提示,这时如果掌握df和du命令是非常明智的选择. df可以查看一级文件夹大小.使用比例.档案系统及其挂入点,但对文件却无能为力. du可以查看文件及文件夹的大小. 两者配 ...

  4. Linux下zip格式文件的解压缩与压缩操作命令详解

    < Linux下zip格式文件的解压缩与压缩操作命令详解 > * 声明:网上找来比较凌乱,整理了一下,方便自己查看 zip格式文件的解压缩与压缩操作: 1.把/home目录下面的huaza ...

  5. linux .pc文件make,简单的驱动makefile详解

    简单的驱动makefile详解 一个工程中的源文件不计数,其按类型.功能.模块分别放在若干个目录中,makefile定义了一系列的规则来指定,哪些文件需要先编译,哪些文件需要后编译,哪些文件需要重新编 ...

  6. linux删除指定大小的文件,Linux下删除空文件,删除指定大小的文件

    Linux下批量删除空文件(大小等于0的文件)的方法: find . -name "*" -type f -size 0c | xargs -n 1 rm -f 用这个还可以删除指 ...

  7. linux中gz文件怎么解压,Linux解压gz文件的命令使用教程及详解

    今天小编给带来一篇linux解压方面的资料 Linux解压gz文件的命令有:gunzip命令.gzip命令.tar命令.下面本篇文章就来带大家了解一下 gz文件是一种压缩文件,以.gz或者.tar.g ...

  8. Linux的tty架构及UART驱动详解

    Linux的tty架构及UART驱动详解 一.模块硬件学习 1.1. Uart介绍 通用异步收发传输器(Universal Asynchronous Receiver/Transmitter),通常称 ...

  9. linux内存管理机制以及free命令详解

    linux内存管理机制以及free命令详解 一.linux内存管理机制 1.物理内存和虚拟内存 直接从物理内存读写数据要比从硬盘读写数据要快的多,因此,我们希望所有数据的读取和写入都在内存完成,而内存 ...

最新文章

  1. android与苹果平板生态,Android和Apple平板电脑的性价比比较
  2. SAP MM ME56不能为审批后的PR分配供应源?
  3. 【原】Java学习笔记028 - 集合
  4. Algorithm:数学建模大赛(国赛和美赛)的简介/内容、数学建模做题流程、历年题目类型及思想、常用算法、常用工具之详细攻略
  5. SharePoint自动化系列——Error features自动deactivate
  6. 【Java多线程】并发时的线程安全:快乐影院示例
  7. CentOS7卸载并安装mysql教程
  8. leetcode35 插入的位置
  9. 区分三个概念:Epoch, Batch, Iteration
  10. android sim卡分析,Android 判断SIM卡属于哪个移动运营商详解及实例
  11. splice删除选中列表_JS之删除数组中的元素的方法如delete和splice
  12. OpenCV3编程入门(毛星云)读书笔记(一)
  13. 适合初中文凭学的计算机技术,初中毕业学啥技术好 最吃香的手艺
  14. 什么是软件测试工程师呢?
  15. ipa文件如何下载安装OR如何设置IPA文件下载链接
  16. IPv6测试.测试您的手机或智能设备的IPv4和IPv6连接性.支持简易模式测试您的手机是否可以连接IPv6网络.支持详细模式测试您的手机是否可以连接IPv6网络
  17. 厦大C语言上机 1413 模式匹配
  18. [ 2204阅读 ] 题型专项 - 句子简化题
  19. linux模拟usb发包,Linux下USB模拟ps2鼠标驱动
  20. Laravel 模型中 $hidden 的作用

热门文章

  1. android 视网膜黄斑检查 amsler,一张图检测黄斑病变,快来测试一下!
  2. 五眼联盟入侵俄罗斯搜索引擎Yandex,美国不予置评
  3. 【幻化万千戏红尘】qianfeng-Android-Day16动画
  4. web服务器可以上传信息吗,Web服务器的架设上传.doc
  5. Lenovo ThinkSystem SR650服务器做raid
  6. Java中的常见的锁及其内存语义
  7. 湖大计算机考研改成408,2018湖大计算机考研专硕回顾
  8. 用openGL实现用黑白相间的棋盘图案填充多边形
  9. 关于css hover动效边缘触发频繁闪动的解决方案
  10. 我对程序员做副业的看法