Qt中Qfile類的使用
1.引言
很多應用程序都具備操作文件的能力,包括對文件進行寫入和讀取,創(chuàng)建和刪除文件等等,甚至某些應用程序的就是為了操作文件,像WPS Office?;诖薗t框架中專門提供了對文件操作的類:QFile。
2.QFile文件操作
QFile類支持對文件進行讀取和寫入,刪除,重命名,拷貝等常見的文件操作,它既可以操作文本文件,也可以用來操作二進制文件。
在Qt代碼中我們使用QFIle類,需要先引入QFile的頭文件:#include <QFile>。常見QFile類對象時,常見的構(gòu)造函數(shù)有:
QFile() QFile(QObject *parent)
參數(shù)parent 用來指定要操作的目標文件,包含文件的存儲目錄和文件名,存儲路徑可以使用絕對地址(比如"D:/Demo/text.txt")或者相對路徑(比如"./Demo/text.txt")。路徑中的分隔符要用"/"表示。
通常情況下,我們一般調(diào)用第二個構(gòu)造函數(shù)來直接指明要操作的文件,對于第一個構(gòu)造函數(shù)而言,我們還需要調(diào)用 setFileName()函數(shù)來指明要操作的文件。
與C++的讀寫規(guī)則一樣,在對文件進行相關(guān)操作之前,我們需要先打開文件,打開文件我們使用 open函數(shù)。常用的語法格式為:
bool QFile::open(OpenMode Mode);
Mode參數(shù)表示不同的打開方式,下列羅列了參數(shù)的可選值和及其不同的含義:
| 打開模式 | 含義 |
|---|---|
| QIODevice::ReadOnly | 以只讀模式打開文件。 |
| QIODevice::WriteOnly | 以只寫模式打開文件。如果文件不存在,將創(chuàng)建新文件;如果文件已存在,其內(nèi)容將被清空。 |
| QIODevice::ReadWrite | 以讀寫模式打開文件。 |
| QIODevice::Append | 以追加模式打開文件,寫入的數(shù)據(jù)將追加到文件末尾,原有內(nèi)容保留。 |
| QIODevice::Truncate | 打開文件時清空其內(nèi)容。通常與 WriteOnly 或 ReadWrite 一起使用。 |
| QIODevice::Text | 在文本模式下打開文件,處理不同平臺的行結(jié)束符(如將 Windows 的 \r\n 轉(zhuǎn)換為 \n)。 |
| QIODevice::Unbuffered | 以非緩沖模式打開文件,數(shù)據(jù)將直接寫入磁盤而不經(jīng)過緩沖區(qū)。 |
根據(jù)需要我們可以一次性選擇多個值,值和值之前使用 |來進行分割,比如:
- QIODevice::ReadOnly|QIODevice::Text表示只允許對文件進行讀操作,讀取文件時,會將行尾結(jié)束符轉(zhuǎn)換為 ‘\n’;
- QIODevice::WriteOnly|QIODevice::Text表示只允許對文件進行寫操作,將數(shù)據(jù)寫入文件時,會將行尾結(jié)束符轉(zhuǎn)換為本地格式;
- QIODevice::ReadWrite|QIODevice::Text| QIODevice::Append
但選擇的多個值之前不能相互沖突,比如比如 Append 和 Truncate 不能同時使用。
如果文件成功打開,open() 函數(shù)返回 true,否則返回 false。
QFile 類提供了很多功能實用的方法,可以快速完成對文件的操作,下表列舉了常用的一些:
| qint64 QFile::size() const | 獲取當前文件的大小。對于打開的文件,該方法返回文件中可以讀取的字節(jié)數(shù)。 |
|---|---|
| bool QIODevice::getChar(char *c) | 從文件中讀取一個字符,并存儲到 c 中。讀取成功時,方法返回 true,否則返回 false。 |
| bool QIODevice::putChar(char c) | 向文件中寫入字符 c,成功時返回 true,否則返回 false。 |
| QByteArray QIODevice::read(qint64 maxSize) | 從文件中一次性最多讀取 maxSize 個字節(jié),然后返回讀取到的字節(jié)。 |
| qint64 QIODevice::read(char *data, qint64 maxSize) | 從文件中一次性對多讀取 maxSize 個字節(jié),讀取到的字節(jié)存儲到 data 指針指定的內(nèi)存控件中。該方法返回成功讀取到的字節(jié)數(shù)。 |
| QByteArray QIODevice::readAll() | 讀取文件中所有的數(shù)據(jù)。 |
| qint64 QIODevice::readLine(char *data, qint64 maxSize) | 每次從文件中讀取一行數(shù)據(jù)或者讀取最多 maxSize-1 個字節(jié),存儲到 data 中。該方法返回實際讀取到的字節(jié)數(shù)。 |
| qint64 QIODevice::write(const char *data, qint64 maxSize) | 向 data 數(shù)據(jù)一次性最多寫入 maxSize 個字節(jié),該方法返回實際寫入的字節(jié)數(shù)。 |
| qint64 QIODevice::write(const char *data) | 將 data 數(shù)據(jù)寫入文件,該方法返回實際寫入的字節(jié)數(shù)。 |
| qint64 QIODevice::write(const QByteArray &byteArray) | 將 byteArray 數(shù)組中存儲的字節(jié)寫入文件,返回實際寫入的字節(jié)數(shù)。 |
| bool QFile::copy(const QString &newName) | 將當前文件的內(nèi)容拷貝到名為 newName 的文件中,如果成功,方法返回 true,否則返回 false。 copy 方法在執(zhí)行復制操作之前,會關(guān)閉源文件。 |
| bool QFile::rename(const QString &newName) | 對當前文件進行重命名,新名稱為 newName,成功返回 true,失敗返回 false。 |
| bool QFile::remove() | 刪除當前文件,成功返回 true,失敗返回 false。 |
3.演示示例
3.1實驗一
演示了 QFile 類讀寫文本文件的過程
#include <QFile>
#include <QDebug>
int main(int argc, char *argv[])
{
//創(chuàng)建 QFile 對象,同時指定要操作的文件
QFile file("D:/demo.txt");
//對文件進行寫操作
if(!file.open(QIODevice::WriteOnly|QIODevice::Text)){
qDebug()<<"文件打開失敗";
}
//向文件中寫入兩行字符串
file.write("hello\r\n");
file.write("world");
//關(guān)閉文件
file.close();
//重新打開文件,對文件進行讀操作
if(!file.open(QIODevice::ReadOnly|QIODevice::Text)){
qDebug()<<"文件打開失敗";
}
//每次都去文件中的一行,然后輸出讀取到的字符串
char * str = new char[100];
qint64 readNum = file.readLine(str,100);
//當讀取出現(xiàn)錯誤(返回 -1)或者讀取到的字符數(shù)為 0 時,結(jié)束讀取
while((readNum !=0) && (readNum != -1)){
qDebug() << str;
readNum = file.readLine(str,100);
}
file.close();
return 0;
}
3.2實驗二【演示 QFile 讀寫二進制文件的過程】
#include <QFile>
#include <QDebug>
int main(int argc, char *argv[])
{
//指定要寫入文件的數(shù)據(jù)
qint32 nums[5]={1,2,3,4,5};
//寫入文件之前,要將數(shù)據(jù)以二進制方式存儲到字節(jié)數(shù)組中
QByteArray byteArr;
byteArr.resize(sizeof(nums));
for(int i=0;i<5;i++){
//借助指針,將每個整數(shù)拷貝到字節(jié)數(shù)組中
memcpy(byteArr.data()+i*sizeof(qint32),&(nums[i]),sizeof(qint32));
}
//將 byteArr 字節(jié)數(shù)組存儲到文件中
QFile file("D:/demo.dat");
file.open(QIODevice::WriteOnly);
file.write(byteArr);
file.close();
//再次打開文件,讀取文件中存儲的二進制數(shù)據(jù)
file.open(QIODevice::ReadOnly);
QByteArray resArr = file.readAll();
//輸出讀取到的二進制數(shù)據(jù)
qDebug()<<"resArr: "<<resArr;
//將二進制數(shù)據(jù)轉(zhuǎn)化為整數(shù)
char* data = resArr.data();
while(*data){
qDebug() << *(qint32*)data;
data += sizeof(qint32);
}
return 0;
}
執(zhí)行程序,demo.dat 文件中會存儲 {1,2,3,4,5} 這 5 個整數(shù)的二進制形式,同時輸出以下內(nèi)容:

4.QFile+QTextStream
與單獨使用QFile類相比,QTextStream類提供了很多讀寫文件相關(guān)的方法,還可以設定寫入到文件的數(shù)據(jù)格式,比如對齊方式,寫入數(shù)據(jù)是否帶前綴等等。
使用QTextStream類之前,程序中需要先引入 頭文件。QTextStream提供了很多構(gòu)造方法,常用的是:
QTextStream(QIODevice *device)
QIODevice 是 QFile 的父類,因此在構(gòu)造 QTextStream 類的對象時,需要傳遞一個 QFile 類的對象。
下表羅列了 QTextStream 類常用的一些方法:
| bool QTextStream::atEnd() const | 判斷是否讀到文件末尾,如果已經(jīng)達到末尾,返回 true,否則返回 false。 |
|---|---|
| QString QTextStream::read(qint64 maxlen) | 從文件中讀最多 maxlen 個字符,返回這些字符組成的 QString 字符串。 |
| QString QTextStream::readAll() | 從文件中讀取所有內(nèi)容,返回由讀取內(nèi)容組成的 QString 字符串。 |
| QString QTextStream::readLine(qint64 maxlen = 0) | 默認讀取一行文本,如果手動指定 maxlen 的值,則最多讀取 maxlen 個字符,并返回讀取內(nèi)容組成的 QString 字符串。 |
| void QTextStream::setFieldAlignment(FieldAlignment mode) | 設置對齊方式,通常與 setFieldWidth() 一起使用。 |
| void QTextStream::setFieldWidth(int width) | 設置每份數(shù)據(jù)占用的位置寬度為 width。 |
QTextStream 類重載了>>輸入運算符和>>輸出運算符,使讀寫文本文件變得更簡單。例如,用 QTextStream 實現(xiàn)【實例一】的程序如下:
#include <QFile>
#include <QDebug>
#include <QString>
#include <QTextStream>
int main(int argc, char *argv[])
{
//創(chuàng)建 QFile 對象,同時指定要操作的文件
QFile file("D:/demo.txt");
//對文件進行寫操作
if(!file.open(QIODevice::WriteOnly|QIODevice::Text)){
qDebug()<<"文件打開失敗";
}
QTextStream out(&file);
//向文件中寫入兩行字符串
out << (QString)"C語言中文網(wǎng)\n" << (QString)"http://c.biancheng.net";
//關(guān)閉文件
file.close();
//重新打開文件,對文件進行讀操作
if(!file.open(QIODevice::ReadOnly|QIODevice::Text)){
qDebug()<<"文件打開失敗";
}
QTextStream in(&file);
//一直讀,直至讀取失敗
while(!in.atEnd()){
QString str;
//從文件中讀取一個字符串
in >> str;
qDebug() << str;
}
file.close();
return 0;
}
和<iostream>類似,QTextStream 類提供了兩種格式化輸出的方法,一種是調(diào)用該類的成員方法,例如表 3 中的 setFieldAlignment()、setFieldWidth 等,另一種是調(diào)用 QTextStream 類提供的格式描述符,下表羅列了常用的一些:
| 描述符 | 功能相同的方法 | 功 能 |
|---|---|---|
| Qt::hex | QTextStream::setIntegerBase(16) | 將指定整數(shù)對應的 16 進制數(shù)寫入到文件中。 |
| Qt::showbase | QTextStream::setNumberFlags(numberFlags() | ShowBase) | 對于非十進制數(shù),寫入到文件中時帶上相應的前綴。二進制數(shù)前綴是 0b,八進制數(shù)前綴是 0,十六進制數(shù)前綴是 0x。 |
| Qt::forcesign | QTextStream::setNumberFlags(numberFlags() | ForceSign) | 將數(shù)字寫入文件時,帶上正負號。 |
| Qt::fixed | QTextStream::setRealNumberNotation(FixedNotation) | 將浮點數(shù)以普通小數(shù)的形式寫入文件。 |
| Qt::scientific | QTextStream::setRealNumberNotation(ScientificNotation) | 將浮點數(shù)以科學計數(shù)法的形式寫入文件。 |
| Qt::left | QTextStream::setFieldAlignment(AlignLeft) | 左對齊 |
| Qt::right | QTextStream::setFieldAlignment(AlignRight) | 右對齊 |
| Qt::center | QTextStream::setFieldAlignment(AlignCenter) | 居中對齊 |
程序運行后,demo.txt 存儲的文本內(nèi)容為:
a3.14 2.7
5.QFile+QDataStream
QDataStream 類的用法和 QTextStream 非常類似,最主要的區(qū)別在于,QDataStream 用于讀寫二進制文件。
使用 QDataStream 類之前,程序中要引入<QDataStream>頭文件。創(chuàng)建 QDataStream 對象常用的構(gòu)造函數(shù)為:
QDataStream::QDataStream(QIODevice *d)
下表羅列了 QDataStream 類常用的成員方法:
| 成員方法 | 功 能 |
|---|---|
| bool QDataStream::atEnd() const | 判斷是否讀到文件末尾,如果已經(jīng)達到末尾,返回 true,否則返回 false。 |
| QDataStream &QDataStream::readBytes(char *&s, uint &l) | 對于用 writeBytes() 方法寫入文件的 l 和 s,只能使用 readBytes() 方法讀取出來。 |
| int QDataStream::readRawData(char *s, int len) | 從文件中讀取最多 len 字節(jié)的數(shù)據(jù)到 s 中,返回值表示實際讀取的字節(jié)數(shù)。注意,調(diào)用該方法之前,需要先給 s 參數(shù)分配好內(nèi)存空間。 |
| void QDataStream::setVersion(int v) | 不同版本的 Qt 中,同名稱的數(shù)據(jù)類型也可能存在差異,通過調(diào)用此方法手動指定版本號,可以確保讀取數(shù)據(jù)的一致性。 |
| int QDataStream::skipRawData(int len) | 跳過文件中的 len 個字節(jié),返回實際跳過的字節(jié)數(shù)。 |
| QDataStream &QDataStream::writeBytes(const char *s, uint len) | 將長度 len 和 s 一起寫入到文件中,對于 writeBytes() 寫入的數(shù)據(jù),只能用 readBytes() 方法讀取。 |
| int QDataStream::writeRawData(const char *s, int len) | 將 s 中前 len 字節(jié)的數(shù)據(jù)寫入文件,返回值表示成功寫入的字節(jié)數(shù)。 |
QDataStream 類也對<<和>>進行了重載,舉個簡單的例子,用 QDataStream 重新實現(xiàn)實例二:
#include <QFile>
#include <QDebug>
#include <QDataStream>
int main(int argc, char *argv[])
{
//指定要寫入文件的數(shù)據(jù)
qint32 nums[5]={1,2,3,4,5};
QFile file("D:/demo.dat");
file.open(QIODevice::WriteOnly);
//創(chuàng)建 QDataStream 對象
QDataStream out(&file);
//將 nums 數(shù)組中的整數(shù)逐個寫入到二進制文件中
for(int i=0;i<5;i++){
out << nums[i];
}
file.close();
//再次打開文件,讀取文件中存儲的二進制數(shù)據(jù)
file.open(QIODevice::ReadOnly);
QDataStream in(&file);
//讀取二進制文件中的數(shù)據(jù)
while(!in.atEnd()){
//每次讀取一個整數(shù)
qint32 num;
in >> num;
qDebug() << num;
}
return 0;
}到此這篇關(guān)于Qt中Qfile類的使用的文章就介紹到這了,更多相關(guān)Qt Qfile類內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
養(yǎng)成良好的C++編程習慣之內(nèi)存管理的應用詳解
"養(yǎng)成良好的編程習慣"其實是相當綜合的一個命題,可以從多個角度、維度和層次進行論述和評判,如代碼的風格、效率和可讀性;模塊設計的靈活性、可擴展性和耦合度等等,要試圖把所有方面都闡述清楚必須花很多的精力,而且也不一定能闡述得全面2013-05-05

