it编程 > 编程语言 > C/C++

Qt中Qfile类的使用

23人参与 2025-05-20 C/C++

1.引言

很多应用程序都具备操作文件的能力,包括对文件进行写入和读取,创建和删除文件等等,甚至某些应用程序的就是为了操作文件,像wps office。基于此qt框架中专门提供了对文件操作的类:qfile。

2.qfile文件操作

qfile类支持对文件进行读取和写入,删除,重命名,拷贝等常见的文件操作,它既可以操作文本文件,也可以用来操作二进制文件。

在qt代码中我们使用qfile类,需要先引入qfile的头文件:#include <qfile>。常见qfile类对象时,常见的构造函数有:

qfile()
qfile(qobject *parent)

参数parent 用来指定要操作的目标文件,包含文件的存储目录和文件名,存储路径可以使用绝对地址(比如"d:/demo/text.txt")或者相对路径(比如"./demo/text.txt")。路径中的分隔符要用"/"表示。

通常情况下,我们一般调用第二个构造函数来直接指明要操作的文件,对于第一个构造函数而言,我们还需要调用 setfilename()函数来指明要操作的文件。

与c++的读写规则一样,在对文件进行相关操作之前,我们需要先打开文件,打开文件我们使用 open函数。常用的语法格式为:

bool qfile::open(openmode mode);

mode参数表示不同的打开方式,下列罗列了参数的可选值和及其不同的含义:

打开模式含义
qiodevice::readonly以只读模式打开文件。
qiodevice::writeonly以只写模式打开文件。如果文件不存在,将创建新文件;如果文件已存在,其内容将被清空。
qiodevice::readwrite以读写模式打开文件。
qiodevice::append以追加模式打开文件,写入的数据将追加到文件末尾,原有内容保留。
qiodevice::truncate打开文件时清空其内容。通常与 writeonly 或 readwrite 一起使用。
qiodevice::text在文本模式下打开文件,处理不同平台的行结束符(如将 windows 的 \r\n 转换为 \n)。
qiodevice::unbuffered以非缓冲模式打开文件,数据将直接写入磁盘而不经过缓冲区。

根据需要我们可以一次性选择多个值,值和值之前使用 |来进行分割,比如:

但选择的多个值之前不能相互冲突,比如比如 append 和 truncate 不能同时使用。

如果文件成功打开,open() 函数返回 true,否则返回 false。

qfile 类提供了很多功能实用的方法,可以快速完成对文件的操作,下表列举了常用的一些:

qint64 qfile::size() const获取当前文件的大小。对于打开的文件,该方法返回文件中可以读取的字节数。
bool qiodevice::getchar(char *c)从文件中读取一个字符,并存储到 c 中。读取成功时,方法返回 true,否则返回 false。
bool qiodevice::putchar(char c)向文件中写入字符 c,成功时返回 true,否则返回 false。
qbytearray qiodevice::read(qint64 maxsize)从文件中一次性最多读取 maxsize 个字节,然后返回读取到的字节。
qint64 qiodevice::read(char *data, qint64 maxsize)从文件中一次性对多读取 maxsize 个字节,读取到的字节存储到 data 指针指定的内存控件中。该方法返回成功读取到的字节数。
qbytearray qiodevice::readall()读取文件中所有的数据。
qint64 qiodevice::readline(char *data, qint64 maxsize)每次从文件中读取一行数据或者读取最多 maxsize-1 个字节,存储到 data 中。该方法返回实际读取到的字节数。
qint64 qiodevice::write(const char *data, qint64 maxsize)向 data 数据一次性最多写入 maxsize 个字节,该方法返回实际写入的字节数。
qint64 qiodevice::write(const char *data)将 data 数据写入文件,该方法返回实际写入的字节数。
qint64 qiodevice::write(const qbytearray &bytearray)将 bytearray 数组中存储的字节写入文件,返回实际写入的字节数。
bool qfile::copy(const qstring &newname)将当前文件的内容拷贝到名为 newname 的文件中,如果成功,方法返回 true,否则返回 false。 copy 方法在执行复制操作之前,会关闭源文件。
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[])
{
    //创建 qfile 对象,同时指定要操作的文件
    qfile file("d:/demo.txt");
    //对文件进行写操作
    if(!file.open(qiodevice::writeonly|qiodevice::text)){
        qdebug()<<"文件打开失败";
    }
    //向文件中写入两行字符串
    file.write("hello\r\n");
    file.write("world");
    //关闭文件
    file.close();

    //重新打开文件,对文件进行读操作
    if(!file.open(qiodevice::readonly|qiodevice::text)){
        qdebug()<<"文件打开失败";
    }
    //每次都去文件中的一行,然后输出读取到的字符串
    char * str = new char[100];
    qint64 readnum = file.readline(str,100);
    //当读取出现错误(返回 -1)或者读取到的字符数为 0 时,结束读取
    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[])
{
    //指定要写入文件的数据
    qint32 nums[5]={1,2,3,4,5};
    //写入文件之前,要将数据以二进制方式存储到字节数组中
    qbytearray bytearr;
    bytearr.resize(sizeof(nums));
    for(int i=0;i<5;i++){
        //借助指针,将每个整数拷贝到字节数组中
        memcpy(bytearr.data()+i*sizeof(qint32),&(nums[i]),sizeof(qint32));
    }
    //将 bytearr 字节数组存储到文件中
    qfile file("d:/demo.dat");
    file.open(qiodevice::writeonly);
    file.write(bytearr);
    file.close();
    //再次打开文件,读取文件中存储的二进制数据
    file.open(qiodevice::readonly);
    qbytearray resarr = file.readall();
    //输出读取到的二进制数据
    qdebug()<<"resarr: "<<resarr;
    //将二进制数据转化为整数
    char* data = resarr.data();
    while(*data){
        qdebug() << *(qint32*)data;
        data += sizeof(qint32);
    }
    return 0;
}

执行程序,demo.dat 文件中会存储 {1,2,3,4,5} 这 5 个整数的二进制形式,同时输出以下内容:

image-20250514104431780

4.qfile+qtextstream

与单独使用qfile类相比,qtextstream类提供了很多读写文件相关的方法,还可以设定写入到文件的数据格式,比如对齐方式,写入数据是否带前缀等等。

使用qtextstream类之前,程序中需要先引入 头文件。qtextstream提供了很多构造方法,常用的是:

qtextstream(qiodevice *device)

qiodevice 是 qfile 的父类,因此在构造 qtextstream 类的对象时,需要传递一个 qfile 类的对象。

下表罗列了 qtextstream 类常用的一些方法:

bool qtextstream::atend() const判断是否读到文件末尾,如果已经达到末尾,返回 true,否则返回 false。
qstring qtextstream::read(qint64 maxlen)从文件中读最多 maxlen 个字符,返回这些字符组成的 qstring 字符串。
qstring qtextstream::readall()从文件中读取所有内容,返回由读取内容组成的 qstring 字符串。
qstring qtextstream::readline(qint64 maxlen = 0)默认读取一行文本,如果手动指定 maxlen 的值,则最多读取 maxlen 个字符,并返回读取内容组成的 qstring 字符串。
void qtextstream::setfieldalignment(fieldalignment mode)设置对齐方式,通常与 setfieldwidth() 一起使用。
void qtextstream::setfieldwidth(int width)设置每份数据占用的位置宽度为 width。

qtextstream 类重载了>>输入运算符和>>输出运算符,使读写文本文件变得更简单。例如,用 qtextstream 实现【实例一】的程序如下:

#include <qfile>
#include <qdebug>
#include <qstring>
#include <qtextstream>
int main(int argc, char *argv[])
{
    //创建 qfile 对象,同时指定要操作的文件
    qfile file("d:/demo.txt");
    //对文件进行写操作
    if(!file.open(qiodevice::writeonly|qiodevice::text)){
        qdebug()<<"文件打开失败";
    }
    qtextstream out(&file);
    //向文件中写入两行字符串
    out << (qstring)"c语言中文网\n" << (qstring)"http://c.biancheng.net";
    //关闭文件
    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 类提供了两种格式化输出的方法,一种是调用该类的成员方法,例如表 3 中的 setfieldalignment()、setfieldwidth 等,另一种是调用 qtextstream 类提供的格式描述符,下表罗列了常用的一些:

描述符功能相同的方法功 能
qt::hexqtextstream::setintegerbase(16)将指定整数对应的 16 进制数写入到文件中。
qt::showbaseqtextstream::setnumberflags(numberflags() | showbase)对于非十进制数,写入到文件中时带上相应的前缀。二进制数前缀是 0b,八进制数前缀是 0,十六进制数前缀是 0x。
qt::forcesignqtextstream::setnumberflags(numberflags() | forcesign)将数字写入文件时,带上正负号。
qt::fixedqtextstream::setrealnumbernotation(fixednotation)将浮点数以普通小数的形式写入文件。
qt::scientificqtextstream::setrealnumbernotation(scientificnotation)将浮点数以科学计数法的形式写入文件。
qt::leftqtextstream::setfieldalignment(alignleft)左对齐
qt::rightqtextstream::setfieldalignment(alignright)右对齐
qt::centerqtextstream::setfieldalignment(aligncenter)居中对齐

程序运行后,demo.txt 存储的文本内容为:

a3.14 2.7

5.qfile+qdatastream

qdatastream 类的用法和 qtextstream 非常类似,最主要的区别在于,qdatastream 用于读写二进制文件。

使用 qdatastream 类之前,程序中要引入<qdatastream>头文件。创建 qdatastream 对象常用的构造函数为:

qdatastream::qdatastream(qiodevice *d)

下表罗列了 qdatastream 类常用的成员方法:

成员方法功 能
bool qdatastream::atend() const判断是否读到文件末尾,如果已经达到末尾,返回 true,否则返回 false。
qdatastream &qdatastream::readbytes(char *&s, uint &l)对于用 writebytes() 方法写入文件的 l 和 s,只能使用 readbytes() 方法读取出来。
int qdatastream::readrawdata(char *s, int len)从文件中读取最多 len 字节的数据到 s 中,返回值表示实际读取的字节数。注意,调用该方法之前,需要先给 s 参数分配好内存空间。
void qdatastream::setversion(int v)不同版本的 qt 中,同名称的数据类型也可能存在差异,通过调用此方法手动指定版本号,可以确保读取数据的一致性。
int qdatastream::skiprawdata(int len)跳过文件中的 len 个字节,返回实际跳过的字节数。
qdatastream &qdatastream::writebytes(const char *s, uint len)将长度 len 和 s 一起写入到文件中,对于 writebytes() 写入的数据,只能用 readbytes() 方法读取。
int qdatastream::writerawdata(const char *s, int len)将 s 中前 len 字节的数据写入文件,返回值表示成功写入的字节数。

qdatastream 类也对<<>>进行了重载,举个简单的例子,用 qdatastream 重新实现实例二:

#include <qfile>
#include <qdebug>
#include <qdatastream>
int main(int argc, char *argv[])
{
    //指定要写入文件的数据
    qint32 nums[5]={1,2,3,4,5};
    qfile file("d:/demo.dat");
    file.open(qiodevice::writeonly);
    //创建 qdatastream 对象
    qdatastream out(&file);
    //将 nums 数组中的整数逐个写入到二进制文件中
    for(int i=0;i<5;i++){
      out << nums[i];
    }
    file.close();

    //再次打开文件,读取文件中存储的二进制数据
    file.open(qiodevice::readonly);
    qdatastream in(&file);
    //读取二进制文件中的数据
    while(!in.atend()){
        //每次读取一个整数
        qint32 num;
        in >> num;
        qdebug() << num;
    }
    return 0;
}

到此这篇关于qt中qfile类的使用的文章就介绍到这了,更多相关qt qfile类内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网! 

(0)

您想发表意见!!点此发布评论

推荐阅读

Qt之QMessageBox的具体使用

05-20

PyQt5 QDate类的具体使用

05-19

C++ map容器插入操作方式详解

05-19

Kotlin 中 infix 关键字的原理和使用场景解析

05-19

VSCode中C/C++安装、配置以及使用的完整指南(适合新手小白)

05-19

PyQt5 QStyleOptionViewItem类的具体使用

05-19

猜你喜欢

版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。

发表评论