今天讨论fstream的实用性用法——fstream可以读或写文件,可以读取文件A的数据稍作修改写入文件B,但如果不想产生一个文件拷贝,那也可以同时读和写一个文件,但是有些情况需要注意。
例如要读取一个reamde.txt文本文件,内容为:
========================================================================
C++/WinRT ConsoleApplication1 Project Overview
123456789012345678+
fstream ffile(L"readme.txt", ios::in | ios::out | ios::binary);
if (!ffile.is_open()) {
cout << "open file failed" << endl;
return;
}
/* 这里先跳过第一行(73字符),读取第二行(51字符),这样读游标来到了124 */
char bufferIn[100] = { 0 };
ffile.seekg(73, ios::beg); /* seekg可以设置读游标 */
ffile.getline(bufferIn, sizeof(bufferIn));
cout << "read buffer1 = " << bufferIn << endl;
/* 读写游标是分开的,移动写游标到第三行开始,并写入"--remember thyme--" */
char bufferOut[50] = { 0 };
strcpy_s(bufferOut, sizeof(bufferOut), "--remember thyme--");
ffile.seekp(73 + strlen(bufferIn) + 1, ios::beg);
ffile.write(bufferOut, 18);
ffile.flush(); /* 这里如果不调用flush,则后面使用read时其游标会错乱,从意想不到的读到数据 */
/* 清空读取buffer,想要读取"--remember thyme--"需要从当前位置回退18个字符,要不然读取到的是"+",因为在+之前写入了18个字符移动了读游标 */
ffile.seekg(-18, ios::cur);
memset(bufferIn, 0, sizeof(bufferIn));
ffile.read(bufferIn, 18);
cout << "read buffer2 = " << bufferIn << endl;
/* 关闭文件 */
ffile.close();
执行上述代码的结果如下:
read buffer1 = C++/WinRT ConsoleApplication1 Project Overview
read buffer2 = --remember thyme--
且readme.txt变为了如下所示:
========================================================================
C++/WinRT ConsoleApplication1 Project Overview
--remember thyme--+