学习记录第二十天

IO文件

操作系统为了方便用户使用系统功能而对外提供的一组系统函数。称之为 系统调用  其中有个  文件IO
一般都是对设备文件操作,当然也可以对普通文件进行操作。

它是一个基于Linux内核的没有缓存的IO机制

特性:
.1 没有缓存区
.2 操作对象不在是流,而是文件描述符
.3文件描述符
很小的非负的整数 int   0-1023
内核每打开一个文件就会获得一个文件 描述符

 每个程序在启动的时候操作系统默认为其打开
  三个描述符与流对象匹配:
  0 ==>STDIN_FILENO === stdin
  1 ==>STDOUT_FILENO == stdout
  2 ==>STDERR_FILENO == stderr

后面创建的文件都从3开始

标准IO和文件IO的后缀

w == O_WRONLY | O_CREAT | O_TRUNC 
w+ == O_RDWR | O_CREAT | O_TRUNC 
r == O_RDONLY 
r+ == O_RDWR
a == O_WRONLY | O_CREAT | O_APPEND
a+ == O_RDWR|O_CREAT|O_APPEND

3.文件IO的操作流程

(1)打开:open
(2)读写:read / write 
(3)关闭:close 

缓冲区

缓冲区

缓冲区是内存空间的一部分。也就是说,在内存空间中预留了一定的存储空间,这些存储空间用来缓冲输入或输出的数据,这部分预留的空间就叫做缓冲区。缓冲区根据其对应的是输入设备还是输出设备,分为输入缓冲区和输出缓冲区。

为什么要引入缓冲区

比如我们从磁盘里取信息,我们先把读出的数据放在缓冲区,计算机再直接从缓冲区中取数据,等缓冲区的数据取完后再去磁盘中读取,这样就可以减少磁盘的读写次数,再加上计算机对缓冲区的操作大大快于对磁盘的操作,故应用缓冲区可大大提高计算机的运行速度。又比如,我们使用打印机打印文档,由于打印机的打印速度相对较慢,我们先把文档输出到打印机相应的缓冲区,打印机再自行逐步打印,这时我们的CPU可以处理别的事情。现在您基本明白了吧,缓冲区就是一块内存区,它用在输入输出设备和CPU之间,用来缓存数据。它使得低速的输入输出设备和高速的CPU能够协调工作,避免低速的输入输出设备占用CPU,解放出CPU,使其能够高效率工作。

行缓冲,1k, terminal,主要用于人机交互stdout
缓存区满或者遇到\n刷新 1024
行缓存多是关于终端的一些操作
1.遇到\n刷新
2.缓存区满刷新
3.程序结束刷新
4.fflush刷新  fflush(stdout);

全缓冲,4k,主要用于文件的读写
缓存区满刷新缓存区 4096
对普通文件进行标准IO操作,建立
的缓存一般为全缓存
刷新条件:
1.缓存区满刷新
2.程序结束刷新
3.fflush来刷新  fflush(fp);
无缓冲,0k  主要用于出错处理信息的输出 stderr 
不对数据缓存直接刷新
printf();==>>stdout 
fprintf(strerr,"fopen error %s",filename);
界面交互 出错处理
使用gdb查看,FILE结构体,或使用写入数据测试缓冲区。
缓冲区的大小是可以设置

open函数

int main(int argc, char *argv[])
{
    int fd= open("1.txt",O_WRONLY | O_CREAT|O_TRUNC,0666);
    if(-1 == fd)
    {
        printf("open error\n");
        return 1;
    }
    printf("fd is %d\n",fd);
    return 0;
}

open("1.c",O_WRONLY|O_CREAT,0666 );
int open(const char *pathname, int flags,int mode);
功能:
获得一个文件描述符
参数:
pathname:文件名
flags:
O_RDONLY |
O_WRONLY
O_RDWR
O_CREAT, 创建文件 
O_EXCL,需要和O_CREAT同时使用,表示新建的文件不能存在,成功,否则open就会失败
O_NOCTTY,不是终端设备
O_TRUNC文件内容清空
O_APPEND追加
O_ASYNC异步io,什么时候io不确定,
O_NONBLOCK非阻塞 


返回值:
成功返回文件描述符
失败返回-1

write函数

int main(int argc, char *argv[])
{
    int fd= open("1.txt",O_WRONLY | O_CREAT|O_TRUNC,0666);
    if(-1 == fd)
    {
        printf("open error\n");
        return 1;
    }
    printf("fd is %d\n",fd);
    char buf[128]="hello,world";
    int wr_ret = write(fd,buf,strlen(buf));
    if(-1 == wr_ret)
    {
        printf("write error\n");
        return 1;
    }
    close(fd);
    return 0;
}

char buf[1024];
ssize_t write(int fd,  const  void *buf, size_t count);
功能:
通过文件描述符向文件中写一串数据
参数:
fd:文件描述符
buf:要写入文件的字符串的首地址
count:要写入字符的个数
返回值:
成功返回实际写入的个数
失败返回-1

read 函数

int main(int argc, char *argv[])
{
    int fd= open("1.txt",O_RDONLY);
    if(-1 == fd)
    {
        printf("open error\n");
        return 1;
    }
    printf("fd is %d\n",fd);

    char buf[512]={0};
    int rd_ret = read(fd,buf,sizeof(buf));
    if(rd_ret<=0)
    {
        printf("read eof or error\n");
        return 1;
    }
    printf("ret %d,%s\n",rd_ret,buf);

    close(fd);
    return 0;
}

ssize_t read(int fd, void *buf, size_t count);
功能:
通过文件描述符读取文件中的数据
参数:
fd:文件描述符
buf:存放数据空间的首地址
count:要读到数据的个数
返回值:
成功返回读到数据的个数
失败返回-1
读到文件结尾返回0

seek函数

int main(int argc, char *argv[])
{
    int fd= open("1.txt",O_WRONLY);
    if(-1 == fd)
    {
        printf("open error\n");
        return 1;
    }
    printf("fd is %d\n",fd);
    off_t offset = lseek(fd,6, SEEK_SET);
    printf("offset %ld\n",offset);
    write(fd,"china",5);
    close(fd);
    return 0;
}

lseek  fseek, rewind ftell
off_t lseek(int fd, off_t offset, int whence);
功能:
定位光标的位置
参数:
fd:文件描述符
offset:偏移量
正:向后偏移
负:向前偏移
零:不偏移
whence:
SEEK_SET
SEEK_CUR
SEEK_END
返回值:
成功返回偏移量
失败返回-1

1、不支持O_APPEND的追加模式,无法生成空洞文件。
2、lseek函数执行失败,文件指针还在偏移前的位置。
3、lseek函数在设备文件上偏移无效。

阻塞:程序因为某种条件没有被触发,而导致'0'   '\0'

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值