C++文件读写详解(ofstream,ifstream,fstream)
1. 概述:
Input/Output library
C++输入输出流的继承关系如图:
1. #include <fstream>
2. ofstream //文件写操作 内存写入存储设备
3. ifstream //文件读操作,存储设备读区到内存中
4. fstream //读写操作,对打开的文件可进行读写操作
2. ofstream
Ø 头文件
#include<fstream>
Ø 继承关系
Ø 功能
文件写操作,内存写入存储设备
Ø open()函数
成员函数open()实现打开文件的操作,从而将数据流和文件进行关联
几种比较常用的打开方式:
1)
以输出的方式打开文件,若文件不存在建立文件,若文件存在将文件长度置为0
fstream fout;
fout.open("D:/1.txt",ofstream::out|ofstream::trunc);//不能用||
if (!fout.is_open())
{
return;//打开失败就返回
}
2) 以输出的方式打开文件,如果没有文件,那么生成空文件;如果有文件,那么清空该文件,写文件的时候是文件指针指向文件末尾(这个是写文件故将文件清空了)()
fout.open("D:/1.txt",ofstream::out|ofstream::ate);//不能用||(若是in则表示将文件的指针移动到文件末尾)
if (!fout.is_open())
{
return;
}
3)
以输出方式打开文件,如果没有文件,那么生成空文件;如果有文件,那么在文件尾追加。写文件的时候是文件指针指向文件末尾
fout.open("D:/1.txt",ofstream::out|ofstream::app);//不能用||
if (!fout.is_open())
{
return;
}
打开文件的方式在类ios(是所有流式I/O类的基类)中定义,常用的值如下:
ios::app: 以追加的方式打开文件
ios::ate: 文件打开后定位到文件尾,ios:app就包含有此属性
ios::binary: 以二进制方式打开文件,缺省的方式是文本方式。两种方式的区别见前文
ios::in: 文件以输入方式打开(文件数据输入到内存)
ios::out: 文件以输出方式打开(内存数据输出到文件)
ios::nocreate: 不建立文件,所以文件不存在时打开失败
ios::noreplace:不覆盖文件,所以打开文件时如果文件存在失败
ios::trunc: 如果文件存在,把文件长度设为0
Ø 示例程序
#include <fstream> //std::ofstream
int main () {
std::ofstream ofs;
ofs.open ("D:/1test.txt",std::ofstream::out | std::ofstream::app);
ofs << "more lorem ipsum"<<end;;
ofs.close();
return0;
3. ifstream
Ø 继承关系
Ø 头文件
#include<fstream>
Ø 示例程序
// print the content of a text file.
#include <iostream> // std::cout
#include <fstream> // std::ifstream
int main () {
std::ifstream ifs;
ifs.open (
"test.txt", std::ifstream::in);
char
c = ifs.get();
while
(ifs.good()) {
std::cout << c;
c = ifs.get();
}
ifs.close();
return
0;
}
4. 二进制文件
1) 在二进制文件中,使用<< 和>>,以及函数(如getline)来操作符输入和输出数据,没有什么实际意义,虽然它们是符合语法的。
2) 文件流包括两个为顺序读写数据特殊设计的成员函数:write 和 read。第一个函数 (write) 是ostream 的一个成员函数,都是被ofstream所继承。而read 是istream 的一个成员函数,被ifstream 所继承。类 fstream 的对象同时拥有这两个函数。
3) 它们的原型是:
write ( char * buffer, streamsize size );
read ( char * buffer,streamsize size );
4) 它们的原型是:
这里 buffer 是一块内存的地址,用来存储或读出数据。参数size 是一个整数值,表示要从缓存(buffer)中读出或写入的字符数。
5) 示例程序
例1
写程序
std::ofstreamoutfile ("D:/new.txt",std::ofstream::out|std::ofstream::binary);//写入文件
if (outfile.is_open())
{
char buf[1024]={0};
strcpy(buf,"huanghao2015082401");
int n=strlen(buf);
cout<<n<<endl;
outfile.write(buf,strlen(buf));
}
读程序
// reading binary file
#include <iostream>
#include <fstream.h>
const char * filename = "D:/new.txt";
int main () {
char * buffer;
long size;
ifstream in (filename,ios::in|ios::binary|ios::ate); //没有将该文件的内容清除掉,这个是读取
size =in.tellg();
in.seekg(0, ios::beg);
buffer =new char [size+1];
memset(buffer,0,size+1);
in.read(buffer, size);
in.close();
cout<< "the complete file is in abuffer";
delete[] buffer;
return 0;
}
//运行结果:
The complete file is in a buffer
例2
读程序
// read a file into memory
#include <iostream> // std::cout
#include <fstream> // std::ifstream
int main () {
std::ifstream is ("test.txt", std::ifstream::binary);
if (is) {
// get length of file:
is.seekg (0, is.end);
int length = is.tellg();
is.seekg (0, is.beg);
char * buffer = new char [length+1];
memset(buffer,0,length+1);
std::cout << "Reading" << length<< "characters... ";
// read data as a block:
is.read (buffer,length);
if (is)
std::cout << "allcharacters read successfully.";
else
std::cout << "error:only " << is.gcount()<< " could beread";
is.close();
// ...buffer contains the entire file...
cout<<endl;
cout<<is.gcount()<<endl;//获取读取的字符数
cout<<buffer<<endl;
delete[] buffer;
}
return 0;
}
例3
写程序(写结构)
void write03()
{
struct record {
char name[10];
int age;
};
struct record array[2]= {{"Ken", 24}, {"Knuth", 28}};
std::ofstreamoutfile ("D:/new.txt",std::ofstream::out|std::ofstream::binary);//写入文件
if (outfile.is_open())
{
outfile.write((char*)array,sizeof(record)*2);
}
}
读程序(读结构体)
void read03()
{
struct record {
char name[10];
int age;
};
struct record array[2];
std::ifstreaminfile ("D:/new.txt",std::ifstream::binary);//读取文件
// get size of file
infile.seekg(0,infile.end);//让读取文件的指针跳转到文件末尾 意思是离文件end处为0
long size = infile.tellg();//计算出文件的字符串长度
infile.seekg(0);//将文件指针指向文件开始位置
infile.read((char*)array,size);
printf("Name1: %s\tAge1: %d\n", array[0].name, array[0].age);
printf("Name2: %s\tAge2: %d\n", array[1].name, array[1].age);
}
例4
写程序(写整数)
void write04()
{
std::ofstreamfout("D:/a.dat",std::ios::binary);
int nNum = 20;
std::stringstr("Hello, world");
fout.write((char*)&nNum, sizeof(int));
fout.write(str.c_str(),sizeof(char) *(str.size()));
fout.close();
}
读程序(读整数)
void read04()
{
std::ifstreamfin("D:/a.dat", std::ios::binary);
int nNum;
char szBuf[256] = {0};
fin.read((char*)&nNum, sizeof(int));
fin.read(szBuf,sizeof(char) *256);
std::cout<< "int = " << nNum<< std::endl;
std::cout<< "str = " << szBuf<< std::endl;
fin.close();
}
5. 按行读取
示例程序
例1(用cin 标准输入)
// istream::getline example
#include <iostream> // std::cin, std::cout
int main () {
char name[256], title[256];
std::cout << "Please,enter your name: ";
std::cin.getline (name,256);
std::cout << "Please,enter your favourite movie: ";
std::cin.getline (title,256);
std::cout << name << "'s favourite movie is " << title;
return 0;
}
例2(ifstream 按行读取)
int getline2()
{
ifstreamifs;
ifs.open("D:/test.ini",ifstream::in);
if (ifs.is_open())
{
char data[256]={0};
while (!ifs.eof())
{
ifs.getline(data,256);
cout<<data<<endl;
memset(data,0,256);
}
}
return 0;
}
6. 关闭(close)
当文件读写操作完成之后,我们必须将文件关闭以使文件重新变为可访问的。成员函数close(),它负责将缓存中的数据排放出来并关闭文件。这个函数一旦被调用,原先的流对象就可以被用来打开其它的文件了,这个文件也就可以重新被其它的进程所访问了。为防止流对象被销毁时还联系着打开的文件,析构函数将会自动调用关闭函数close。