1 理論
C語言中檔案打開模式涉及到:r、w、a、+、t、b(記憶:我日,變态啊)等字元,其中:
- r 代表 read
- w 代表 write
- a 代表 append
- + 代表可讀可寫
- t 代表text(文本)
- b 代表binary(二進制)
通過對上述字元的組合指定檔案打開模式,可以表明檔案:
- 當檔案不存在時,建立 or 提示打開失敗?(無論是讀還是寫,都要先打開檔案)
- 打開檔案後,檔案指針位于 檔案開頭 or 檔案末尾?
- 可讀?
- 可寫?
- 寫檔案時,覆寫原有檔案 or 清空原有檔案 or 在原有檔案末尾追加?
具體情況見下表(不對 t、b 進行說明)
模式 | r | r+ | w | w+ | a | a+ |
---|---|---|---|---|---|---|
檔案不存在 | 打開失敗 | 打開失敗 | 建立 | 建立 | 建立 | 建立 |
檔案指針 | 讀開頭 | 讀寫開頭 | 寫開頭 | 讀寫開頭 | 寫末尾 | 讀開頭、寫末尾 |
讀 | ✓ \checkmark ✓ | ✓ \checkmark ✓ | × \times × | ✓ \checkmark ✓ | × \times × | ✓ \checkmark ✓ |
寫 | × \times × | ✓ \checkmark ✓ | ✓ \checkmark ✓ | ✓ \checkmark ✓ | ✓ \checkmark ✓ | ✓ \checkmark ✓ |
覆寫 or 清空 or 追加 | 不支援寫 | 覆寫 | 清空 | 清空 | 追加 | 追加 |
//測試代碼
#include <stdio.h>
#include <iostream>
using namespace std;
//為了使fopen可用(fopen是不安全的)
#pragma warning(disable:4996)
void testOpen(char* name, char* mode) {
FILE *fp = fopen(name, mode);
if (!fp)
{
cout << "Open the file failed!" << endl;
}
else
{
//隻有成功打開了,才能關閉,貿然關閉會導緻bug
fclose(fp);
}
}
void testWrite(char* name, char* mode) {
char buf[10] = { 65,66,67,68,69 };
FILE *fp = fopen(name, mode);
if (!fp)
{
cout << "Open the file failed!" << endl;
}
else
{
int count = fwrite(buf, 1, 5, fp);
cout << count << endl;
fclose(fp);
}
}
void testRead(char* name, char* mode) {
FILE *fp = fopen(name, mode);
if (!fp)
{
cout << "Open the file failed!" << endl;
}
else
{
char first;
first = fgetc(fp);
if (first != EOF)
{
cout << first << endl;
}
fclose(fp);
}
}
int main()
{
//此時工程根目錄沒有文本檔案
//testOpen("test1.txt", "r"); //隻提示打開檔案失敗
//testOpen("test2.txt", "r+"); //隻提示打開檔案失敗
//testOpen("test3.txt", "w"); //建立檔案test3.txt
//testOpen("test4.txt", "w+"); //建立檔案test4.txt
//testOpen("test5.txt", "a"); //建立檔案test5.txt
//testOpen("test6.txt", "a+"); //建立檔案test6.txt
//工程檔案6個文本檔案均存在,且内容均為@@@@@@@@@@(10個)
//testWrite("test1.txt", "r"); //寫入失敗,内容依舊為@@@@@@@@@@
//testWrite("test2.txt", "r+"); //寫入成功,内容為[email protected]@@@@(直接從頭開始覆寫)
//testWrite("test3.txt", "w"); //寫入成功,内容為ABCDE(先清空後覆寫)
//testWrite("test4.txt", "w+"); //寫入成功,内容為ABCDE(先清空後覆寫)
//testWrite("test5.txt", "a"); //寫入成功,内容為@@@@@@@@@@ABCDE(直接在尾部追加)
//testWrite("test6.txt", "a+"); //寫入成功,内容為@@@@@@@@@@ABCDE(直接在尾部追加)
//工程檔案6個文本檔案均存在,且内容均為@@@@@@@@@@(10個)
//testRead("test1.txt", "r"); //讀取成功,讀取到第一個字元@
//testRead("test2.txt", "r+"); //讀取成功,讀取到第一個字元@
//testRead("test3.txt", "w"); //不支援讀
//testRead("test4.txt", "w+"); //支援讀,但檔案内容均已被清空,什麼都沒讀到
//testRead("test5.txt", "a"); //不支援讀
//testRead("test6.txt", "a+"); //讀取成功,讀取到第一個字元@
system("pause");
return 0;
}
2 結論
打開檔案
- r、r+ 模式打開檔案:若檔案不存在,則提示打開檔案失敗,并不建立檔案;若檔案存在,正常打開;
- w、w+ 模式打開檔案:若檔案不存在,則建立檔案;若檔案存在,正常打開,并清空檔案中内容;
- a、a+ 模式打開檔案:若檔案不存在,則建立檔案;若檔案存在,正常打開;
讀檔案
- r、r+ 模式讀檔案:從檔案開頭起讀取檔案内容;
- w、w+ 模式讀檔案:w模式不支援讀;w+模式支援讀,但由于打開檔案會先清空内容,是以一開始也是讀不到内容的;
- a、a+ 模式讀檔案:a模式不支援讀;a+模式支援讀,并且不同于寫,會從檔案開頭讀取檔案内容;
寫檔案
- r、r+ 模式寫檔案:r 模式不支援寫;r+ 模式支援寫,從檔案開頭寫入新的内容,會覆寫舊的内容,可能會存在新舊内容共存現象;
- w、w+ 模式寫檔案:均先清空檔案内容,然後從頭開始寫入新的内容,所有内容均為新的内容;
- a、a+ 模式寫檔案:均從檔案末尾寫入新的内容,新舊内容同時存在;
3 備注
- w、w+模式打開檔案會導緻檔案被清空,慎用!
- 讀寫二進制檔案則添加 b 字元;讀寫文本檔案則添加 t 字元。