FILE *fopen(const char *restrict pathname, const char *type);
FILE *freopen(const char *restrict pathname, const char *type, FILE *restrict fp);//将一个指定的文件打开为一个预定义的流
FILE *fdopen(int fd, const char *type);
//成功,返回文件指针;失败,返回NULL
int fwide(FILE *fp, int mode);
//<0, 字节定向;>0,宽定向;=0,未定向
void setbuf(FILE *restrict fp, char *restrict buf);
int setvbuf(FILE *restrict fp, char *restrict buf, int mode, size_t size);//_IOFBF,_IOLBF,_IONBF
//成功,返回0;失败,返回非0
int getc(FILE *fp);
int fgetc(FILE *fp);
int getchar(void);
//成功,返回下一个字符;失败,返回EOF
char *fgets(char *restrict buf, int n, FILE *restrict fp);
//成功,返回buf;文件尾或失败,返回NULL
int ungetc(int c, FILE *fp);//将字符c压入流fp
//成功,返回c;失败,返回EOF
int fclose(FILE *fp);
int fflush(FILE *fp);
//成功,返回0;失败,返回EOF
int putc(int c, FILE *fp);
int fputc(int c, FILE *fp);
int putchar(int c);
//成功,返回c;出错,返回EOF
int fputs(const char *restrict str, FILE *restrict fp);
//成功,返回非负值;出错,返回EOF
int fread(char *restrict ptr, size_t size, size_t nobj, FILE *restrict fp); //一次读取一个完整的结构,size:每个对象的大小,nobj:对象的个数
int write(const char *restrict ptr, size_t size, size_t nobj, FILE *restrict fp); //一次写一个完整的结构,size:每个对象的大小,nobj:对象的个数
//返回读写的字节数;
long ftell(FILE *fp);//返回当前偏移量
int fseek(FILE *fp, long offset, int whence);//设置偏移量
void rewind(FILE *fp);//将一个流设置到文件的起始位置
格式化I/O
int printf(const char *restrict format, ...);
int fprintf(FILE *restrict fp, const char *restrict format, ...);
int dprintf(int fd, const char *restrict format, ...);
成功:返回输出字符数;失败,返回负值
int sprintf(char *restrict buf, const char *restrict format, ...);
int snprintf(char *restrict buf, size_t n, const char *restrict format, ...); //解决sprintf的缓冲区会溢出的问题
成功:返回存入数组的字符数;出错,返回负值
int scanf(const char *restrict format, ...);
int fscanf(FILE *restrict fp, const char *restrict format, ...);
int sscanf(const char *restrict buf, const char *restrict format, ...);
//每个标准的I/O流都有一个与其相关联的文件描述符
int fileno(FILE *fp); //获得fp的fd
写个程序,练习一下:
#include <stdio.h>
#include <wchar.h>
#include <unistd.h>
#include <fcntl.h>
#define BUFSIZE 100
int main()
{
FILE *pfile = NULL;
FILE *pfile2 = NULL;
int fd, n;
char buf[BUFSIZE];
//输出文件file内容到屏幕
fd = open("file", O_RDONLY);
if (fd == -1)
{
printf("open() error\n");
exit(-1);
}
n = read(fd, buf, BUFSIZE);
if (n == -1)
{
printf("read() error\n");
exit(-1);
}
if (write(STDOUT_FILENO, buf, n) != n)
{
printf("write() error\n");
exit(-1);
}
pfile = fopen("file", "r+");
if (pfile == NULL)
exit(-1);
printf("fopen() ok\n");
pfile2 = freopen("newfile", "w", stderr);//将"newfile"设置为标准输出
if (pfile2 == NULL)
exit(-1);
printf("freopen() ok\n");
pfile2 = fdopen(open("newfile", O_RDONLY), "r");
if (pfile2 == NULL)
exit(-1);
printf("fdopen() ok\n");
int status;
status = fwide(pfile, -1);//将流pfile设置为字节定向
if (status >= 0)
exit(-1);
printf("fwide() ok\n");
setbuf(pfile2, NULL);//关闭缓冲
printf("setbuf() ok\n");
status = setvbuf(pfile, buf, _IOFBF, BUFSIZE);
if (status != 0)
exit(-1);
printf("setvbuf() ok\n");
int c = getc(pfile);
if (c == EOF)
exit(-1);
printf("getc() ok, letter from pfile is: %c\n", c);
c = fgetc(pfile);
if (c == EOF)
exit(-1);
printf("fgetc() ok, letter from pfile is: %c\n", c);
printf("enter a letter: ");
c = getchar();//从标准输入读
if (c == EOF)
exit(-1);
printf("getchar() ok, your input is: %c\n", c);
if (ungetc(c, pfile) == EOF)//字母c压入流缓冲区
exit(-1);
printf("ungetc() ok\n");
if (fgets(buf, BUFSIZE, pfile) == NULL)//fgets遇到换行符终止
exit(-1);
printf("fgets() ok, now, buf is: %s\n", buf);
c = 'b';
if (putc(c, pfile) == EOF)
exit(-1);
printf("putc() ok\n");
if (fputc(c, pfile) == EOF)
exit(-1);
printf("fputc() ok\n");
if (putchar(c) == EOF)//输出到屏幕
exit(-1);
printf("\nputchar() ok\n");
if (fputs(buf, pfile) == EOF)
exit(-1);
printf("fputs() ok\n");
fseek(pfile, 0, SEEK_SET);//偏移量设置到文件起始位置
printf("fseek() ok, now offset is: %d\n", ftell(pfile));
if (fread(buf, 1, 5, pfile) != 5)//一次读取5个1字节
exit(-1);
printf("fread() ok\n");
if (fwrite(buf, 1, 5, stdout) != 5)//一次写5个1字节
exit(-1);
printf("\nfwrite() ok\n");
printf("ftell() ok, now offset is: %d\n", ftell(pfile));
rewind(pfile);//将一个流设置到文件的起始位置
printf("rewind() ok, now offset is: %d\n", ftell(pfile));
printf("fileno() ok, fd of pfile is : %d\n", fileno(pfile));//获取流的文件描述符
fseek(pfile, 0, SEEK_END);
fprintf(pfile, "something come from fprintf()\n");//标准输出到流pfile
fclose(pfile);
fclose(pfile2);
return 0;
}
结果如下:
分析:
1.调用open、read、write输出文件file内容
2.调用fopen流pfile,打开后流pfile和文件file绑定在一起,因为后面要写入流,所以用"r+"
3.调用freopen,将流文件newfile设置为标准错误
4.在文件描述符上打开一个流
5.-1,小于0,设置为字节定向
6.setbuf的参数为NULL,代表关闭缓冲;否则是全缓冲或行缓冲
7.pfile设置为全缓冲,_IOFBF、_IOLBF、_IONBF
8.getc读取一个字符,宏;fgetc读取一个字符,函数;getchar从标准输入读
9.用ungetc压入字符到流的缓冲区中,并未写到底层文件中。
10.fgets一次读取一行,遇到换行符终止;不用gets,因为不能手动设置缓冲区大小,可能会造成缓冲区溢出
11.putc输出一个字符,宏;fputc输出一个字符,函数;fputc输出到标准输出
12.fputs一次输出一行;不用puts,因为不能手动设置缓冲区大小,可能会造成缓冲区溢出
13.ftell返回偏移量,fseek设置偏移量,rewind设置流偏移量到文件起始位置 SEEK_CUR SEEK_SET SEEK_END
14.fread、fwrite用于二进制文件,一次读写指定大小指定数量的对象
15.fprintf标准输出到流
16.关闭流,文件被关闭前,冲洗缓冲区输出数据,丢弃缓冲区输入数据