标准IO文件流可用于单字符或多字符字符集,流的定向(orientation)决定了所读,写的字符是单字符还是多字符的。
当一个流被最初创建时,它并没有定向。
如果在未定向的流上使用一个多字节IO函数(<wchar.h>),则将该流的定向设置为宽定向的。
如果在未定向的流上使用一个单字节IO函数,则流的定向设置为单字节定向。
#include <stdio.h>
#include <wchar.h>
/* 若mode参数值为负,fwide尝试将流设置为单字节定向 */
/* 若mode参数值为正,fwide尝试将流设置为多字节定向 */
/* 若mode参数值为0,fwide不设置定向,只是返回该流的定向 */
int fwide(FILE* fp, int mode); /* 返回值表示流的定向,正为宽定向,负为但定向,0为未定向*/
注意:
#include <stdio.h>
FILE* fopen(const char* path,const char* type);
FILE* freopen(const char* path,const char* type,FILE* fp);
FILE* fdopen(int filedes,const char* type);
#include <stdio.h>
int getc(FILE* fp);
int fgetc(FILE* fp);
int getchar();
int ungetc(int c,FILE* fp);
int putc(int c,FILE* fp);
int fputc(int c,FILE* fp);
int putchar(int c);
其中getc和fgetc的区别为,getc可能为宏,而fgetc一定是函数. 即
putc和fputc的区别类似于getc和fgetc的区别.
#include <stdio.h>
char* fgets(char* buf,int n,FILE* fp);
char* gets(char* buf);
int fputs(const char* str,FILE* fp);
int puts(const char* str);
注意:
#include <stdio.h>
size_t fread(void* ptr,size_t size,size_t ntimes,FILE* fp);
size_t fwrite(const void* ptr,size_t size,size_t ntimes,FILE* fp);
#include <stdio.h>
long ftell(FILE* fp);
int fseek(FILE* fp,long offset,int whence);
void rewind(FILE* fp);
off_t ftello(FILE* fp);
int fseeko(FILE* fp,off_t offset,int whence);
int fgetpos(FILE* fp,fpos_t* pos);
int fsetpos(FILE* fp,const fpos_t* pos);
读取出错或到达文件结尾,读取函数的返回值都是同一个值. 为了区分这两种不同的情况,必须调用ferror或feof
#include <stdio.h>
int ferror(FILE* fp);
int feof(FILE* fp);
void clearerr(FILE* fp);
#include <stdio.h>
int fileno(FILE* fp);
标准IO提供了2种类型的缓冲
填满IO缓冲区才进行实际的IO操作
对于驻留在磁盘上的文件,通常是由标准IO库实施全缓冲.
当输入和输出中遇到换行符时,标准IO库执行IO操作
当流涉及一个终端时,通常使用行缓冲.
一般标准IO缓冲的惯例为:标准出错不带缓冲,打开至终端设备的流是行缓冲,其他流是全缓冲.
#include <stdio.h>
void setbuf(FILE* fp,char* buf);
int setvbuf(FILE* fp,char* buf,int mode,size_t size);
当为打开缓冲机制时,这里参数buf必须为一个长度为BUFSIZ的缓冲区(BUFSIZ定义在stdio.h中)
若要关闭缓冲机制,参数buf为NULL
| _IOFBF | 全缓冲 |
| _IOLBF | 行缓冲 |
| _IONBF | 无缓冲 |
#include <stdio.h>
int fflush(FILE* fp);
<stdio.h>中预定义了三个文件指针:stdin,stdout和stderr 一般来说,stderr不带缓冲,stdin和stdout为行缓冲
#include <stdio.h>
char* tmpnam(char* ptr);
char* tempnam(const char* directory,const char* prefix);
FILE* tmpfile();
int mkstemp(char* template);
PSOXI.1提供了以线程安全的方式管理FILE文件的方法. 可以使用`flockfile'和`ftrylockfile'获取与FILE对象关联的锁,且这个锁为递归锁.
所有操作FILE对象的标准IO函数,都需要表现的好像内部调用了flockfile和funlockfile一样,即不能出现多个线程同时写入同一FILE对象时出现乱序的情况.
#include <stdio.h>
int ftrylockfile(FILE* fp);
void flockfile(FILE* fp);
void funlockfile(FILE* fp);
通过这些函数,我们可以把多个标准IO函数的调用组合成一个原子序列.
若标准IO函数每次操作都获取自己的锁再释放,那么在进行单字符的IO操作时,会消耗大量的性能到加解锁中,因此就有了 不加锁的基于字符的标准IO函数
#include <stdio.h>
int getchar_unlocked();
int getc_unlocked(FILE* fp);
int putchar_unlocked(int c);
int putc_unlocked(int c,FILE* fp);
请保证这四个函数调用时包含在flockfile/ftrylockfile和funlockfile中

