本章講述標準I/O庫ide
流和FILE對象函數
對於標準I/O庫,它們的操做是圍繞流進行的。流的定向決定了所讀、寫的字符是單字節仍是多字節的。spa
#include <stdio.h> #include <wchar.h> int fwide(FILE *fp,int mode);
fwide函數可用於流的定向。根據mode參數的不一樣值,fwide函數執行不一樣的工做rest
若mode參數值爲負,fwide將試圖使指定的流是字節定向的code
若mode參數值爲正,fwide將試圖使指定的流是寬定向的orm
若mode參數值是0,fwide將不試圖設置流的定向,但返回標誌該流定向的值對象
當一個流最初被建立時,它並無定向。若在未定向的流上使用一個多字節(單字節)I/O函數,則將該流設置爲寬(字節)定向。fwide並不改變已定向流的定向。blog
標準輸入、標準輸出和標準錯誤進程
對一個進程預約義了3個流:stdin、stdout、stderr。字符串
緩衝
標準I/O提供瞭如下3種類型的緩衝
1 全緩衝,在這種狀況下,在填滿標準I/O緩衝區後才進行實際I/O操做。如磁盤上的文件一般實施全緩衝。
2 行緩衝,在這種狀況下,當在輸入和輸出中遇到換行符,標準I/O執行I/O操做。如標準輸入輸出。
3 不帶緩衝,標準I/O庫不對字符進行緩衝存儲。標準錯誤流stderr一般是不帶緩衝的。
咱們能夠調用下面兩個函數更改緩衝類型
#include <stdio.h> void setbuf(FILE *restrict fp,char *restrict buf); int setvbuf(FILE *restrict fp,char *buf,int mode,size_t size);
能夠使用setbuf打開或關閉緩衝機制,參數buf指定一個長度爲BUFSIZ的緩衝區。將buf設置爲NULL能夠關閉緩衝。
使用setvbuf,咱們能夠精確地說明所需的緩衝類型。這是用mode參數實現的:
_IOFBF 全緩衝
_IOLBF 行緩衝
_IONBF 不帶緩衝
咱們能夠經過fflush函數沖洗一個流
#include <stdio.h>
int fflush(FILE *fp);
打開流
下面3個函數打開一個標準I/O流
#include <stdio.h> FILE *fopen(const char *restrict pathname,const char *restrict type); FILE *freopen(const char *restrict pathname,const char *restrict type,FILE *restrict fp); FILE *fdopen(int fd,const char *type);
type參數指定對該I/O流的讀、寫方式,ISO C規定type參數能夠有以下15種不一樣的值
其中b做爲type的一部分,這使得標準I/O系統能夠區分文本文件和二進制文件
調用fclose關閉一個打開的流
#include <stdio.h>
int fclose(FILE *fp);
讀和寫流
如下3個函數可用於一次讀一個字符
#include <stdio.h> int getc(FILE *fp); int fgetc(FILE *fp); int getchar(void); //等同於getc(stdin)
對應上面所述的每一個輸入函數都有一個輸出函數
#include <stdio.h> int putc(int c,FILE *fp); int fputc(int c,FILE *fp); int putchar(int c);
每次一行I/O
下面兩個函數提供每次輸入一行的功能
#include <stdio.h> char *fgets(char *restrict buf,int n,FILE *restrict fp); //buf爲緩衝區地址,讀入的行將送入其中,參數n指定緩衝的長度 char *gets(char *buf); //不推薦使用
fputs和puts提供每次輸出一行的功能
#include <stdio.h> int fputs(const char *restrict str,FILE *restrict fp); int puts(const char *str);
二進制I/O
下列兩個函數執行二進制I/O操做
#include <stdio.h> size_t fread(void *restrict ptr,size_t size,size_t nobj,FILE *restrict fp); size_t fwrite(const void *restrict ptr,size_t size,size_t nobj,FILE *restrict fp);
參數size爲欲寫結構的長度,nobj爲欲寫的元素個數,函數返回的是讀或寫的對象數。這些函數有如下兩種常見的用法
float data[10]; if(fwrite(&data[2],sizeof(float),4,fp)!=4) err_sys("fwrite error");
//讀寫一個結構 struct{ short count; long total; char name[NAMESIZE]; }item; if(fwrite(&item,sizeof(item),1,fp)!=1) err_sys("fwrite error");
定位流
有3種方法定位標準I/O流
#include <stdio.h> long ftell(FILE *fp); //若成功,則返回當前文件位置指示,出錯則返回-lL int fseek(FILE *fp,long offset,int whence); void rewind(FILE *fp);
除了偏移量的類型是off_t而非long之外,ftello函數與ftell相同,fseeko函數與fseek相同
#include <stdio.h> off_t ftello(FILE *fp); int fseeko(FILE *fp,off_t offset,int whence);
下面函數是ISO C標準引入的
#include <stdio.h> int fgetpos(FILE *restrict fp,fpos_t *restrict pos); int fsetpos(FILE *fp,const fpos_t *pos);
格式化I/O
格式化輸出是由printf函數處理的
#include <stdio.h> 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,...); //參數n指定緩衝區長度
執行格式化輸入處理的是3個scanf函數
#include <stdio.h> 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,...);
臨時文件
ISO C標準I/O庫提供了兩個函數以幫助建立臨時文件
#include <stdio.h> char *tmpnam(char *ptr); FILE *tmpfile(void);
tmpnam函數產生一個與現有文件名不一樣的一個有效路徑名字符串
tmpfile建立一個臨時二進制文件(類型wb+),在關閉該文件或程序結束時將自動刪除。