第五章 標準I O庫

2021-07-14 04:49:30 字數 4400 閱讀 9051

1. fwide函式

用於設定流的定向。

int fwide(file *fp, int mode);  //若流是寬定向,返回正值;是位元組定向,返回負值;是未定向,返回0。

如若mode是負值,則函式試圖使指定的流是位元組定向的;如果mode是正值,則函式試圖使制定的流是寬定向的;若mode引數值為0,函式不試圖設定流的定向,返回標識流定向的值。

2. 緩衝

全緩衝,

行緩衝和

不帶緩衝

標準錯誤時不帶緩衝的,開啟至終端裝置的流是行緩衝的,其他流是全緩衝的。

void setbuf(file *restrict fp, char *restrict buf);

用setbuf開啟或者關閉緩衝機制,當buf指向乙個長度為bufsize的緩衝區,在此之後的流就是全緩衝的(對於乙個與終端裝置相關的流,可能不一樣);當buf為null時,代表關閉緩衝。

int setvbuf(file *restrict fp, char *restrict buf, int mode, size_t size);

mode的引數: _iofbf(全緩衝),_iolbf(行緩衝),_ionbf(不帶緩衝)。

int fflush(file *fp); //清洗流,當fp是null時,導致所有的輸出流被清洗

3. 開啟流

fopen,freopen和fdopen。

file *freopen(const char *restrict pathname, const char *restrict type, file *restrict fp);

file *fdopen(int fd, const char *type); //常用於由建立管道和網路通訊通道函式返回的描述符。

4. 讀和寫流

輸入函式:getc,fgetc,getchar。

檔案的尾端或者出錯,呼叫上面的函式,返回都是eof;為了區分這個,呼叫ferror或feof。

int ungetc(int c, file *fp); //從流中讀取資料後,可以呼叫ungetc將字元再壓送回流

輸出函式:putc,fputc,putchar。

5. 每次一行i/o

char *fgets(char *restrict buf, int n, file *restrict fp); 

char *gets(char *restrict buf);  //不太安全,當輸入長度大於緩衝區長度

對應的輸出函式是fputs和puts。

6. 二進位制i/o

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);

7. 定位流

i. ftell和fseek函式,還有rewind函式可將乙個流設定到檔案的起始位置。

ii. ftello和fseeko函式

iii. fgetpos和fsetpos

8. 格式化i/o

格式化輸出

i. int printf(const char *restrict format, ...);

ii. int fprintf(file *restrict fp, const char *restrict format,);

iii. int dprintf(int fd, const char *restrict format, ...) //寫到指定檔案描述符

ix. int spintf(char *restrict buf, const char *restrict format, ...) //將格式化的字元送入陣列中

x. int snprintf(char *restrict buf, size_t n, const char *restrict format, ...) //跟上面的類似,就是可以控制數量n,防止溢位。

格式化輸入

scanf,fscanf,sscanf函式

9. 實現細節

int fileno(file *fp); //獲得與流相關聯的檔案描述符

測試三種標準流:連線終端輸入流和輸出流都是行緩衝,檔案的輸入輸出流是全緩衝,錯誤的是不帶緩衝的。

#include "apue.h"

void pr_stdio(const char*, file*);

int is_unbuffered(file*);

int is_linebuffered(file*);

int buffer_size(file*);

int main(void)

void pr_stdio(const char* name, file* fp)

#if defined(_io_unbuffered)

int is_unbuffered(file* fp)

int is_linebuffered(file *fp)

int buffer_size(file *fp)

#elif defined(__snbf)

int is_unbuffered(file *fp)

int is_linebuffered(file *fp)

int buffer_size(file *fp)

#elif defined(_ionbf)

#ifdef _lp64

#define _flag __pad[4]

#define _ptr __pad[1]

#define _base __pad[2]

#endif

int is_unbuffered(file *fp)

int is_linebuffered(file *fp)

int buffer_size(file *fp)

#else

#error unknown stdio implementation

#endif

10. 臨時檔案

char *tmpnam(char *ptr); //產生乙個與現有檔名不同的乙個有效路徑名字串

file *tmpfile(void); //建立乙個臨時二進位制檔案,在關閉該檔案或者程式結束時自動刪除這個檔案

#include "apue.h"

int main(void)

相對而言mkstemp更安全一些

char *mkdtemp(char *template); //新建乙個臨時目錄

int *mkstemp(char *template); //新建乙個臨時檔案,返回檔案描述符

#include "apue.h"

#include void make_temp(char *template);

int main()

void make_temp(char *template)

else

}

mkstemp與tmpfile不同,建立的臨時檔案不會自動刪除的。

第一種情況因為使用了陣列,名字是在棧上分配的;但是第二種情況使用的是指標,在這種情況下,只有指標駐留在棧上。編譯器把字串放在了可執行檔案的唯讀段,當mkstemp函式試圖修改字串時,出現了段錯誤。

11. 記憶體流

file *fmemopen(void *retrict buf, size_t size, const char *restrict type); //建立記憶體流

#include "apue.h"

#define bsz 48

int main()

輸出如下:

initial buffer contents: 

before flush: //流沖洗後緩衝區才會變化

after flush: hello, world

len of string in buf = 12

after fseek: bbbbbbbbbbbbhello, world//fseek引起緩衝區沖洗

len of string in buf = 24

after fclose: hello, worldcccccccccccccccccccccccccccccccccc

len of string in buf = 46

還有另外兩個函式

file *open_memstream(char **bufp, size_t *sizep);          //建立的流是面向位元組的

file *open_wmemstream(wchar_t **bufp, size_t *sizep);  //建立的流是面向寬位元組的

p173

第五章 標準I O庫

本章用於解析c語言標準i o庫,之所以在unix類系統的程式設計中會介紹c語言標準庫,主要是因為unix和c之間具有密不可分的關係。標準i o庫相比於作業系統的i o庫,具有更高的效率和可移植性,前者是因為標準i o庫提供了緩衝和塊長度優化功能,後者是因為使用標準i o庫的 不僅能在各unix系統上...

APUE筆記 第五章 標準I O庫

2.流和相關函式 3.格式化i o 4.fileno 函式 5.tmpnam 和tmpfile 函式 標準i o庫是在系統呼叫函式基礎上構造的。ansi c要求下列快取特徵 1 當且僅當標準輸入和標準輸出並不涉及互動作用裝置時,它們才是全快取的。2 標準出錯決不會是全快取的。1.1全快取 在這種情況...

python第五章 Python學習(第五章)

記錄所有的名片字典 card list defshow menu 顯示資訊 print 50 print 歡迎使用 名片管理系統 v1.0 print print 1.新增名片 print 2.顯示全部 print 3.搜尋名片 print print 0.退出系統 print 50 defnew ...