国产一级a片免费看高清,亚洲熟女中文字幕在线视频,黄三级高清在线播放,免费黄色视频在线看

打開APP
userphoto
未登錄

開通VIP,暢享免費(fèi)電子書等14項(xiàng)超值服

開通VIP
C++中對二進(jìn)制文件的讀寫操作
二進(jìn)制文件不是以ASCII代碼存放數(shù)據(jù)的,它將內(nèi)存中數(shù)據(jù)存儲(chǔ)形式不加轉(zhuǎn)換地傳送到磁盤文件,因此它又稱為內(nèi)存數(shù)據(jù)的映像文件。因?yàn)槲募械男畔⒉皇亲址麛?shù)據(jù),而是字節(jié)中的二進(jìn)制形式的信息,因此它又稱為字節(jié)文件。

對二進(jìn)制文件的操作也需要先打開文件,用完后要關(guān)閉文件。在打開時(shí)要用ios::binary指定為以二進(jìn)制形式傳送和存儲(chǔ)。二進(jìn)制文件除了可以作為輸入文件或輸出文件外,還可以是既能輸入又能輸出的文件。這是和ASCII文件不同的地方。

一、用成員函數(shù)read和write讀寫二進(jìn)制文件

對二進(jìn)制文件的讀寫主要用istream類的成員函數(shù)read和write來實(shí)現(xiàn)。這兩個(gè)成員函數(shù)的原型為
   istream& read(char *buffer,int len);
   ostream& write(const char * buffer,int len);
字符指針buffer指向內(nèi)存中一段存儲(chǔ)空間。len是讀寫的字節(jié)數(shù)。調(diào)用的方式為
   a. write(p1,50);
   b. read(p2,30);
例.14 將一批數(shù)據(jù)以二進(jìn)制形式存放在磁盤文件中。
#include <fstream>
using namespace std;
struct student
{
   char name[20];
   int num;
   int age;
   char sex;
};
int main( )
{
   student stud[3]={"Li",1001,18,'f',"Fun",1002,19,'m',"Wang",1004,17,'f'};
   ofstream outfile("stud.dat",ios::binary);
   if(!outfile)
   {
      cerr<<"open error!"<<endl;
      abort( );//退出程序
   }
   for(int i=0;i<3;i++)
      outfile.write((char*)&stud[i],sizeof(stud[i]));
      outfile.close( );
   return 0;
}
其實(shí)可以一次輸出結(jié)構(gòu)體數(shù)組的個(gè)元素,將for循環(huán)的兩行改為以下一行:
   outfile.write((char*)&stud[0],sizeof(stud));
執(zhí)行一次write函數(shù)即輸出了結(jié)構(gòu)體數(shù)組的全部數(shù)據(jù)。

可以看到,用這種方法一次可以輸出一批數(shù)據(jù),效率較高。在輸出的數(shù)據(jù)之間不必加入空格,在一次輸出之后也不必加回車換行符。在以后從該文件讀入數(shù)據(jù)時(shí)不是靠空格作為數(shù)據(jù)的間隔,而是用字節(jié)數(shù)來控制。
例.15 將剛才以二進(jìn)制形式存放在磁盤文件中的數(shù)據(jù)讀入內(nèi)存并在顯示器上顯示。
#include <fstream>
using namespace std;
struct student
{
   string name;
   int num;
   int age;
   char sex;
};
int main( )
{
   student stud[3];
   int i;
   ifstream infile("stud.dat",ios::binary);
   if(!infile)
   {
      cerr<<"open error!"<<endl;
      abort( );
   }
   for(i=0;i<3;i++)
   infile.read((char*)&stud[i],sizeof(stud[i]));
   infile.close( );
   for(i=0;i<3;i++)
   {
      cout<<"NO."<<i+1<<endl;
      cout<<"name:"<<stud[i].name<<endl;
      cout<<"num:"<<stud[i].num<<endl;;
      cout<<"age:"<<stud[i].age<<endl;
      cout<<"sex:"<<stud[i].sex<<endl<<endl;
   }
   return 0;
}
運(yùn)行時(shí)在顯示器上顯示:
NO.1
name: Li
num: 1001
age: 18
sex: f

NO.2
name: Fun
num: 1001
age: 19
sex: m

NO.3
name: Wang
num: 1004
age: 17
sex: f
請思考: 能否一次讀入文件中的全部數(shù)據(jù),如
   infile.read((char*)&stud[0],sizeof(stud));

二、與文件指針有關(guān)的流成員函數(shù)

在磁盤文件中有一個(gè)文件指針,用來指明當(dāng)前應(yīng)進(jìn)行讀寫的位置。對于二進(jìn)制文件,允許對指針進(jìn)行控制,使它按用戶的意圖移動(dòng)到所需的位置,以便在該位置上進(jìn)行讀寫。文件流提供一些有關(guān)文件指針的成員函數(shù)。

幾點(diǎn)說明:
  1. 這些函數(shù)名的第一個(gè)字母或最后一個(gè)字母不是g就是p。
  2. 函數(shù)參數(shù)中的“文件中的位置”和“位移量”已被指定為long型整數(shù),以字節(jié)為單位?!皡⒄瘴恢谩笨梢允窍旅嫒咧?
       ios::beg文件開頭(beg是begin的縮寫),這是默認(rèn)值。
       ios::cur指針當(dāng)前的位置(cur是current的縮寫)。
       ios::end文件末尾。
    它們是在ios類中定義的枚舉常量。舉例如下:
       infile.seekg(100);//輸入文件中的指針向前移到字節(jié)位置
       infile.seekg(-50,ios::cur);    //輸入文件中的指針從當(dāng)前位置后移字節(jié)
       outfile.seekp(-75,ios::end);   //輸出文件中的指針從文件尾后移字節(jié)

三、隨機(jī)訪問二進(jìn)制數(shù)據(jù)文件

一般情況下讀寫是順序進(jìn)行的,即逐個(gè)字節(jié)進(jìn)行讀寫。但是對于二進(jìn)制數(shù)據(jù)文件來說,可以利用上面的成員函數(shù)移動(dòng)指針,隨機(jī)地訪問文件中任一位置上的數(shù)據(jù),還可以修改文件中的內(nèi)容。
例.16 有個(gè)學(xué)生的數(shù)據(jù),要求:
(1) 把它們存到磁盤文件中;
(2) 將磁盤文件中的第,3,5個(gè)學(xué)生數(shù)據(jù)讀入程序,并顯示出來;
(3) 將第個(gè)學(xué)生的數(shù)據(jù)修改后存回磁盤文件中的原有位置。
(4) 從磁盤文件讀入修改后的個(gè)學(xué)生的數(shù)據(jù)并顯示出來。

要實(shí)現(xiàn)以上要求,需要解決個(gè)問題:
(1) 由于同一磁盤文件在程序中需要頻繁地進(jìn)行輸入和輸出,因此可將文件的工作方式指定為輸入輸出文件,即ios::in|ios::out|ios::binary。
(2) 正確計(jì)算好每次訪問時(shí)指針的定位,即正確使用seekg或seekp函數(shù)。
(3) 正確進(jìn)行文件中數(shù)據(jù)的重寫(更新)。

可寫出以下程序:
#include <fstream>
using namespace std;
struct student
{
   int num;
   char name[20];
   float score;
};
int main( )
{
   student stud[5]={1001,"Li",85,1002,"Fun",97.5,1004,"Wang",54,1006,"Tan",76.5,1010,"ling",96};
   fstream iofile("stud.dat",ios::in|ios::out|ios::binary);
   //用fstream類定義輸入輸出二進(jìn)制文件流對象iofile
   if(!iofile)
   {
      cerr<<"open error!"<<endl;
      abort( );
   }
   for(int i=0;i<5;i++)//向磁盤文件輸出個(gè)學(xué)生的數(shù)據(jù)
      iofile.write((char *)&stud[i],sizeof(stud[i]));
   student stud1[5];                  //用來存放從磁盤文件讀入的數(shù)據(jù)
   for(int i=0;i<5;i=i+2)
   {
      iofile.seekg(i*sizeof(stud[i]),ios::beg);  //定位于第,2,4學(xué)生數(shù)據(jù)開頭
      iofile.read((char *)&stud1[i/2],sizeof(stud1[0]));//先后讀入個(gè)學(xué)生的數(shù)據(jù),存放在stud1[0],stud[1]和stud[2]中
      cout<<stud1[i/2].num<<" "<<stud1[i/2].name<<" "<<stud1[i/2].score<<endl;//輸出stud1[0],stud[1]和stud[2]各成員的值
   }
   cout<<endl;
   stud[2].num=1012;                         //修改第個(gè)學(xué)生(序號為)的數(shù)據(jù)
   strcpy(stud[2].name,"Wu");
   stud[2].score=60;
   iofile.seekp(2*sizeof(stud[0]),ios::beg);   //定位于第個(gè)學(xué)生數(shù)據(jù)的開頭
   iofile.write((char *)&stud[2],sizeof(stud[2])); //更新第個(gè)學(xué)生數(shù)據(jù)
   iofile.seekg(0,ios::beg);                       //重新定位于文件開頭
   for(int i=0;i<5;i++)
   {
      iofile.read((char *)&stud[i],sizeof(stud[i]));  //讀入個(gè)學(xué)生的數(shù)據(jù)
      cout<<stud[i].num<<" "<<stud[i].name<<" "<<stud[i].score<<endl;
   }
   iofile.close( );
   return 0;
}

運(yùn)行情況如下:
1001 Li 85(第個(gè)學(xué)生數(shù)據(jù))
1004 Wang 54        (第個(gè)學(xué)生數(shù)據(jù))
1010 ling 96        (第個(gè)學(xué)生數(shù)據(jù))

1001 Li 85          (輸出修改后個(gè)學(xué)生數(shù)據(jù))
1002 Fun 97.5
1012 Wu 60          (已修改的第個(gè)學(xué)生數(shù)據(jù))
1006 Tan 76.5
1010 ling 96
本程序?qū)⒋疟P文件stud.dat指定為輸入輸出型的二進(jìn)制文件。這樣,不僅可以向文件添加新的數(shù)據(jù)或讀入數(shù)據(jù),還可以修改(更新)數(shù)據(jù)。利用這些功能,可以實(shí)現(xiàn)比較復(fù)雜的輸入輸出任務(wù)。

請注意,不能用ifstream或ofstream類定義輸入輸出的二進(jìn)制文件流對象,而應(yīng)當(dāng)用fstream類。
本站僅提供存儲(chǔ)服務(wù),所有內(nèi)容均由用戶發(fā)布,如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請點(diǎn)擊舉報(bào)。
打開APP,閱讀全文并永久保存 查看更多類似文章
猜你喜歡
類似文章
C/C++文件流的操作
看了大量外界禁傳的資源,才發(fā)現(xiàn)輸入輸出是這樣的意思
第十三章 文 件
B+ 樹實(shí)現(xiàn)程序
C++移動(dòng)和獲取文件讀寫指針(seekp、seekg、tellg、tellp)
C++文件
更多類似文章 >>
生活服務(wù)
分享 收藏 導(dǎo)長圖 關(guān)注 下載文章
綁定賬號成功
后續(xù)可登錄賬號暢享VIP特權(quán)!
如果VIP功能使用有故障,
可點(diǎn)擊這里聯(lián)系客服!

聯(lián)系客服