語言文件系統稱為流文件(Stream),正文流(正文文件),二進制流(二進制文件)

  • 緩沖與非緩沖文件
  • 順序操作文件與隨機操作文件
    • 順序文件:讀/寫第K個數據塊之前必須讀/寫第1至K-1個數據塊;
    • 隨機文件:可直接讀/寫第K個數據塊;
  • 正文文件的操作一般是順序文件;
  • 二進制文件的操作都是隨機文件。


    一、文件操作的一般過程

定義文件指針 FILE *
打開文件 fopen
對文件進行讀寫

二、系統已定義的與文件操作有關的數據結構全都在stdio.h中

  1. FILE 結構體

       FILE *fr,*fp,*fw;

    FILE* 指針作為文件句柄,是文件訪問的唯一標識,它由fopen函數創建,fopen打開文件成功,則返回一個有效的FILE*指針,否則返回空指針NULL

  2. 標準文件指針

       FILE *stdin,*stdout,*stderr,
       stdin 指鍵盤輸入
       stdout 指顯示器
       stderr 指出錯輸出設備,也指顯示器

    這些變量已成功初始化,可直接使用.

三、常用操作函數

  1. fopen

    格式:FILE *fopen(文件名字符串,打開方式串)

    例:FILE *fr; fr=fopen("c:\\user\\abc.txt","r");

    字符串操作:

    1)"r"或"rt":正文文件只讀方式打開。文件不存在,則打開失敗(順序讀)"w"或"wt":正文文件只寫方式打開。若文件不存在,則建立文件;若文件存在,則刪除文件內容,重建空文件(順序寫);(截取文件長度為0)

    2) "a"或"at":正文文件添加方式。文件不存在,則建立文件(順序添加寫)

    3) "r+"或"rt++":正文文件讀寫打開,文件不存在,則打開失敗(順序讀/寫、隨機讀/寫,含改寫與添加);

    4) "w+"或"w++":正文文件讀寫方式打開,文件不存在,則建立文件;否則截取文件長度為0(順序讀/寫,隨機讀/寫,對寫入的內容可以讀或改寫或添加)

    5) ~b:正文文件→二進制文件
      順序讀→順序/隨機讀(“rb”)

      eg:"r"或"rt"→"rb"
       順序寫("wb")
       順序添加寫("ab")
       順...,隨...,含...("rb+")
       順...,添加("wb+")
       順...,添加("ab+")

    使用fopen時,但凡含r字母的打開方式,一定要加判斷,文件是否打開成功,否則程序不會報告錯誤,會運行下去。

    如:FILE *fr;
    fr=fopen("abc.txt","r");
    if(fr==NULL){
    printf("File not open!\n");
    return; /*或exit(1);*/

  2. 文件關閉

    fclose(FILE *fp)

    一般地,fclose(fp)與fopen應配對使用,特別是含有寫方式的文件,若不關閉會造成文件數據丟失。

    fcloseall(void):關閉當前所有打開的文件。

  3. 單字節的輸入函數

    可適用于二進制與正文文件操作
    int fgetc(FILE *fp)
       int fputc(char ch.FILE *fp)

    fgetc的返回值都是正數(0~255)

    文件無可讀字節則返回-1(EOF)

    正文文件與二進制文件讀寫的區別:
    正文文件讀到13 10時,將自動跳過13,讀出10并返回;正文文件寫入10時,首先自動寫入13再寫入10.

  4. 文件指針與文件指針操作函數

    文件指針是文件操作系統數據結構內部的一種數據指針,它用于標注文件當前讀寫位置,C語言中,文件指針以字節為單位,文件第一個字節位置號為0,若文件長度為N個字節,則最后一個字節的位置號為N-1,長度為N字節的文件有效讀寫范圍為0~N-1。指針位置在此之外進行讀/寫操作,則失敗;讀寫函數返回-1(EOF);

    C語言的文件指針采用long型值;

    執行文件讀/寫操作后,文件指針自動向后移動,指到新的待讀/寫位置。

    文件指針移動函數
    rewind(FILE *fp)
    文件指針重置為0
    fseek(FILE *fp,long off,int pos)
       從pos位置開始,移動off個字節。

    pos: 0 文件開始
          1 文件當前指針位置
          2 文件結尾(文件長度為N,則指針位置為N)

    例:fseek(fp,0l,0);←→rewind(fp)
    fseek(fp,-1L,2); /*移動指針到最后一個字節*/
    fseek(fp,-2L,1); /*移動指針到當前位置的前兩個位置*/
    long ftell(FILE *fp)

    求當前指針位置

    例:求文件長度
    fseek(fp,OL,2);
    len=ftell(fp);
    則len為文件長度


    文件指針的特性:

  • 可在“負無窮”到“正無窮”任意移動;
  • 在0~N-1之外進行讀操作,則讀失敗;讀失敗后,feof函數為真;
  • 從N位置開始寫入,則為添加;
  • 從0~N位置之外開始寫也可,其行為不必掌握,因為幾乎無用;
  • 無論任何方式,剛打開文件時,ftell函數返回值都是0,含a方式的文件,只要一寫(第一次寫),文件指針自動移動到N位置處。
    int feof(FILE *fp)
    若文件讀失敗,則返回非0值,否則返回0值;僅用于讀是否到文件尾。
    任何fseek操作使feof為假,即使文件指針在0~N-1之外。
  1. 正文文件讀/寫函數
    fscanf(fp...)
       fprintf(fp...)

    其中,...與scanf和printf用法完全相同.
    scanf(...)←→fscanf(stdin...)
    printf(...)←→fprintf(stdout...)

  2. 二進制文件讀/寫函數,即字節塊函數
    int fread(char *buf,int size,int count,FILE *fp)
       int fwrite(char *buf,int&nbtp;size,int count,FILE *fp)
    從文件讀出size x count個字節到內存塊buf;從內存塊buf寫入size x count個字節到文件,返回實際讀出/寫入的字節數。


?



一、文件中刪除第K個記錄:拷貝0~K-1,K+1~N條記錄到一個臨時文件,刪除源文件,將源文件改名為源文件。

二、讀/改寫第K個記錄:移動指針到第K個記錄,用fread,fwrite改寫。

三、添加記錄(略)

四、插入記錄

  1. 復制臨時文件
  2. 插入到K號記錄之前:先將N-1寫入N位置,N-2寫入N-1,直到K寫入K+1位置:用待插入記錄改寫K位置。(建立時用rb+方式打開)

    #include "tdio.h"
    void main()
    {FILE *fp;char ch1,ch2;long pos1,pos2,p;
    char fname[81];
    printf("Input C source filename:");
    gets(fname);
    fp=fopen(fname,"r+");
    if(!fp){printf("FILE not found .\n); return;
    ch1=fgetc(fp);
    while(!feof(fp))
    {cha2=fgetc(fp);if(feof(fp)) break;
    if(ch1=='/'&&ch2=='*')
    {pos1=ftell(fp)-2;
    }
    if(ch1=='*'&&ch=='/')
    {pos2=ftell(fp)-1;
    fseek(fp,pos1,0);
    for(p=pos1;p<=pos2;p++) fputc(32,fp);
    fseek(fp,OL,1);
    }
    ch1=ch2;
    }
    fclose(fp);