每个程序在启动的时候操作系统默认为其打开
三个描述符与流对象匹配:
0 ==>STDIN_FILENO === stdin
1 ==>STDOUT_FILENO == stdout
2 ==>STDERR_FILENO == stderr
stdin,stdout,stderr,===>FILE*
特性:
.1 没有缓存区 (//可以认为数据直接交给了内核 )
.2 操作对象不在是流(FILE *),而是文件描述符(整数)
.3文件描述符
很小的非负的整数 int 0-1023
内核每打开一个文件就会获得一个文件 描述符
---------------------------------
库函数:
优点:
a.方便,功能多
b.可移植性好
标准
不足:
c.可能存在 安全性 隐患
系统调用:
优点:
a.使用起来,简单 ,功能简单
b.安全性高
c.设备文件 ---- 文件IO ///dev/video0 ----> fopen();
缺点:
c.很多复杂功能需要自己封装设计
d.可移植性差
-----------------
标准IO库: 系统调用
fopen open
r O_RDONLY
w O_WRONLY|O_CREAT|O_TRUNC
r+ O_RDWR
w+ O_RDWR |O_CREAT|O_TRUNC
a O_WRONLY|O_CREAT|O_APPEND
a+ O_RDWR |O_CREAT|O_APPEND
-------------------
库函数 本质上是 对系统调用 的封装
-----------------------------------------------------------------------------------------------------------
在字符串中插入字符串:
先获取总长度len,把插入地方剩下的一半读入buf,再在n的位置写入字符串,写入buf
-----------------------------------------------------------------------------
统计文件中字母的个数并打印:
---------------------------------------------------------------
1. open();------------------------------------------------------------------------------
man 2 open
成功返回文件描述符,失败返回 -1并置errno
"r" --- O_RDONLY
"r+" --- O_RDWR
"w" --- O_WRONLY|O_CREAT|O_TRUNC , 0666
"w+" --- O_RDWR|O_CREAT|O_TRUNC , 0666
"a" --- O_WRONLY|O_APPEND|O_CREAT,0666
"a+" --- O_RDWR|O_APPEND|O_CREAT,0666
2. close();----------------------------------------------------------------------------
功返回0,失败返回-1
3. read();-------------------------------------------------------------------------------
man 2 read
从文件fp中读取存入buf中
注意:count是一次读取的字节数,不是元素个数;
用printf %s输出字符串要注意改两个地方,添加 ‘\0’
4. write();-------------------------------------------------------------------------------
man 2 write
5. lseek();--------------------------------------------------------------------------------------
注意:成功返回偏移量,不需要调用类似ftell函数
获取文件大小:
off_t sizeFile = lseek(fd,0,SEEK_END); //从头到尾的偏移量 就是文件大小
在创立空洞文件时,少写一步ftell,“”相当于空字符串‘\0’,但是不能直接写 ‘\0’,因为需要的是地址
od -c <filename> 查看二进制文件
用read和write实现文件拷贝,在拷贝前,两文件的偏移量应都偏到开头
read不能用strlen,若buf为{0},则strlen也为0了;write也不能用strlen,因为不能保证buf里是字符串,应用有效字符个数ret
注意:定位操作不支持追加
6. fileno();-------------------------------------------------------------
流指针转文件描述符
int fd = fileno(stdin); //流指针转文件描述符
7. fdopen();--------------------------------------------------------------------
失败返回NULL,并置errno
FILE *fp = fdopen(fd, "w"); //文件描述符转流指针
fdopen() 的打开模式尽量兼容之前fd打开时的模式
总结:
open 成功返回文件描述符 | 失败返回 -1并置errno
read(从哪里读的文件描述符,要存放的地址buf,要读的字节个数)
成功返回读到的数据个数 | 失败返回 -1 读到文件结尾返回0
write(准备写进去的文件描述符,已有数据的地址buf,要写的字符个数)
成功返回写入的字符个数 | 失败返回 -1 并置errno
lseek 成功返回偏移量 | 失败返回-1
fileno 成功返回文件描述符 | 失败返回 -1
fdopen 成功返回文件流 | 失败返回NULL,并置errno