C++学习手记六:C++文件处理

C++文件操作的常见头文件分别为<iostream>和<fstream>

本文规定输入流(stream input)的方向是从文件到程序的流,输出流为程序到文件的流。

顺序存取文件读写:

向硬盘中写入文件示例(C++11 Chap 14.3 p.g.447):

// Fig. 14.3: fig14_03.cpp
// Create a sequential file.
#include <iostream>
#include <string>
#include <fstream> // contains file stream processing types
#include <cstdlib> // exit function prototype
using namespace std;

int main()
{
   // ofstream constructor opens file                
  ofstream outClientFile("../Read_From_File/clients.txt", ios::out);
   
   //Can also be written as this because ios::out is by default:             
   //ofstream outClientFile( "../Read_From_File/clients.txt" );
//   //Can also be written as:
//   ofstream outClientFile;
//   outClientFile.open("../Read_From_File/clients.txt");
   
   // exit program if unable to create file
   if ( !outClientFile ) // overloaded ! operator
   {
      cerr << "File could not be opened" << endl;
      exit( EXIT_FAILURE );
   } // end if

   cout << "Enter the account, name, and balance." << endl
      << "Enter end-of-file to end input.\n? ";

   int account; // the account number
   string name; // the account owner's name
   double balance; // the account balance

   // read account, name and balance from cin, then place in file
   while ( cin >> account >> name >> balance )
   {
      outClientFile << account << ' ' << name << ' ' << balance << endl;
      cout << "? ";
   } // end while

    outClientFile.close();
} // end main

一般地,C++文件有以下几种打开方式:

  • ios::app,打开文件,并使得输出流从文件结尾位置开始输出
  • ios::ate,打开文件,并指向文件结尾(通常也是用于扩展文件)
  • ios::in,打开文件,启用输入流
  • ios::out,若文件已经存在,打开并清空文件;若文件不存在,新建文件。启用输出流写数据
  • ios::trunc,清空原文件中的内容
  • ios::binary,以二进制形式打开文件,准备读写二进制流

在程序中读取硬盘文件示例:

// Fig. 14.6: fig14_06.cpp
// Reading and printing a sequential file.
#include <iostream>
#include <fstream> // file stream
#include <iomanip>
#include <string>
#include <cstdlib> // exit function prototype
using namespace std;

void outputLine( int, const string &, double ); // prototype

int main()
{
   // ifstream constructor opens the file          
   ifstream inClientFile( "clients.txt", ios::in );

   // exit program if ifstream could not open file
   if ( !inClientFile ) 
   {
      cerr << "File could not be opened" << endl;
      exit( EXIT_FAILURE );
   } // end if

   int account; // the account number
   string name; // the account owner's name
   double balance; // the account balance

   cout << left << setw( 10 ) << "Account" << setw( 13 ) 
      << "Name" << "Balance" << endl << fixed << showpoint;

   // display each record in file
   while ( inClientFile >> account >> name >> balance )
      outputLine( account, name, balance );
} // end main

// display single record from file
void outputLine( int account, const string &name, double balance )
{
   cout << left << setw( 10 ) << account << setw( 13 ) << name
      << setw( 7 ) << setprecision( 2 ) << right << balance << endl;

} // end function outputLine

在顺序存取文件中,光标所指的字符位置可以通过seekg(对于输入流来说)以及seekp(对于输出流来说)进行更改,可以通过tellp和tellg获得。这两个函数的使用示例如下(C++11 Chap 14.4 p.g.452):

//光标指向文件的第n字节,默认模式ios::beg
fileObj.seekg(n); 或
//fileObj.seekg(n, ios::beg);
//由于ios::beg为默认模式,因此可以不指定

//光标指向文件从当前位置往后算n字节:
fileObj.seekg(n, ios::cur);

//光标指向文件结尾往回算第n字节:
fileObj.seekg(n, ios::end);

//获取光标当前位置:
long location = fileObj.tellg();

fileObj.clear()往往与fileObj.seekp(n)配合使用,用于清除当前光标状态并重新寻找文件中相应的位置。

在I/O操作中,remove(char * path)函数(头文件<stdio.h>)用于删除已存在的文件,但需要注意删除之前必须先关闭文件。

随机存取文件读写

随机存取文件是指文件中任何内容的搜索成本都是O(1)的文件。随机存取文件往往以对象的形式存储整块内容,由于每块内容大小相同,因此通过寻找相应的块号码则可以快速读取文件内容。由于大量的块事实上可能是空块,因此随机存取策略是一个典型的用空间换时间的流存取策略(C++11 Chap 14.9 p.g.466)

随机存取文件初始化示例如下:

ofstream outCredit( “credit.dat”, ios::out | ios::in | ios::binary);
//If can not open, generate error information, similar as examples above:
if(!outCredit){...}

//Suppose ClientData is an already defined class
ClientData blankClient;

for(int i = 0; i < 100; i++)
    outCredit.write( reinterpret_cast<const char *>( &blankClient), sizeof(ClientData) );

写入/更新示例如下:

// seek position in file of user-specified record
      outCredit.seekp( ( client.getAccountNumber() - 1 ) * 
         sizeof( ClientData ) );

      // write user-specified information in file
      outCredit.write( reinterpret_cast<char *>(&client),
         sizeof( ClientData ) );

读取示例如下:

//Prototype of output function:
void outputLine( ostream&, const ClientData & ); 
//in main:
ifstream inCredit( "../RandomAccessProject/credit.txt", ios::in | ios::binary );
// read all records from file
   while ( inCredit && !inCredit.eof() ) 
   {
      // display record
      if ( client.getAccountNumber() != 0 )
         outputLine( cout, client );

      // read next from file
      inCredit.read( reinterpret_cast< char * >( &client ),
         sizeof( ClientData ) );
   } // end while

转载于:https://my.oschina.net/Samyan/blog/1236288

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值