Qt5文件及磁盘处理

9.1.1 读写文本文件
Qt提供了QFile类用于进行文件操作。QFile类提供了读写文件的接口,可以读写文本文件,二进制文件和Qt的资源文件。
处理文本文件和二进制文件,可以使用QTextStream类和QDataStream类。处理临时文件可以使用QTemporaryFile,获取文件信息可以使用QFileInfo,处理目录可以使用
QDir,监视文件和目录变化可以使用QFileSystemWatcher。

#include <QCoreApplication>
#include <QFile>
#include <QtDebug>
 
 
/*
 * 打开一个文件有两种方式。一种方式是在构造函数中指文件名;另一种方式是使用setFileName()函数设置文件名。
 *
 * 打开文件使用open()函数,关闭文件使用close()函数。此处的open()函数以只读方式打开文件,只读方式参数为
 * QIODevice::ReadOnly,只写方式参数为QIODevice::WriteOnly,读写参数为QIODevice::ReadWrite。
 *
 * qint64 lineLen = file.readLine(buffer, sizeof(buffer)):在QFile中可以使用从QIODevice中继
 * 承的readLine()函数读取文件中的一行。
 *
 * if(LineLen != -1){qDebug() << buffer}:如果读取成功,则readLine()函数返回实际读取的字节数;如果
 * 读取失败,则返回“-1”
 *
*/
int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);
 
 
    QFile file("textFile1.txt");
 
 
    if(file.open (QIODevice::ReadOnly))
    {
        char buffer[1024];
 
 
        qint64 LineLen = file.readLine (buffer, sizeof(buffer));
 
 
        if(LineLen != -1)
        {
            qDebug() << buffer;
        }
    }
 
 
    file.close ();
 
 
    return a.exec();
}

9.1.2 QTextStream类读写文本
QTextStream提供了更为方便的接口来读写文本,它可以操作QIODevice、QByteArray和QString。使用QTextStream的流操作符,可以方便地读写单词、行和数字。
为了产生文本,QTextStream还提供了填充、对齐和数字格式化的选项。

#include <QCoreApplication>
#include <QFile>
#include <QTextStream>
 
 
/*
 * 将内容写入到文件中
 * 
 * if(data.open(QFile::WriteOnly | QFile::Truncate))表示将原来文件中的内容清空。输出时将格式设为左对齐,占10个
 * 字符位置。
 * 
 * out << QObject::tr ("score:") << qSetFileWidth(10) << left << 90 <<endl:用户使用格式化函数和流操作符设
 * 置需要的输出格式。其中,qSetFieldWidth ()函数是设置字宽度的格式化函数。除此之外,QTextStream还提供了其他一些格式
 * 化函数
*/
int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);
 
 
    QFile data("data.txt");
 
 
    if(data.open(QFile::WriteOnly|QFile::Truncate))
    {
        QTextStream out(&data);
        out<<QObject::tr("score:")<<qSetFieldWidth(10)<<left<<90<<endl;
    }
 
 
    return a.exec();
}


QTextStream的格式化函数

函数 功能描述
qSetFieldWidth(int width)
设置字段宽度
qSetPadChar(Qchar ch)
设置填充字符
qSetRealNumberPercision(int precision)
设置实数精度

QTextStream的流操作符


操作符 作用描述
bin
设置读写的整数为 二进制数
oct
设置读写的整数为 八进制数
dec
设置读写的整数为十进制数
hex
设置读写的整数为十六进制数
showbase
强制显示进制前缀,如十六进制(0x)、八进制(0)、二进制(0b)
forcesign
强制显示符号(+、-)
forcepoint
强制显示小数点
noshowbase 强制不显示前缀
noforcesign 强制不显示符号
uppercasebase
显示大写的进制前缀
lowercasebase
显示小些的进制前缀
uppercasebase 用大写字母表示
lowercasebase 用小些字母表示
fixed 固定小数点表示
scientific 科学计数法表示
left 左对齐
right 右对齐
center 居中
endl 换行
flush 清除缓冲

9.2 读写二进制文件
QDateStream类提供了将二进制文件串行化的功能,用于实现C++基本类数据类型,如char,short,int,char*等的串行化。更复杂的串行化操作则是通过将数据分解为
基本类型完成的。

运行效果:


mainwindow.h

#ifndef MAINWINDOW_H
#define MAINWINDOW_H
 
 
#include <QMainWindow>
 
 
class MainWindow : public QMainWindow
{
    Q_OBJECT
 
 
public:
    MainWindow(QWidget *parent = 0);
    ~MainWindow();
 
 
    void filefun();
};
 
#endif   //   MAINWINDOW_H
mainwindow.cpp
#include "mainwindow.h"
#include <QFile>
#include <QtDebug>
#include <QDataStream>
#include <QDate>
 
 
MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent)
{
    filefun ();
}
 
 
MainWindow::~MainWindow()
{
}
 
 
void MainWindow::filefun ()
{
    /*将二进制数据写到数据流*/
    QFile file("binary.dat");
    file.open (QFile::WriteOnly | QFile::Truncate);
    QDataStream out(&file);                                 //将数据序列化
    out << QString(tr("张卫东:"));                           //将字符串序列化
    out << QDate::fromString ("1990/04/01", "yyyy/MM/dd");    //讲整数序列化
    out << (qint32)25;
    file.close ();
 
 
    /*从文件中读取数据*/
    file.setFileName ("binary.dat");
    if(!file.open (QFile::ReadOnly))
    {
        qDebug() << "error" << endl;
        return;
    }
 
 
    QDataStream in(&file);
    QString name;
    QDate birthday;
    qint32 age;
 
 
    in >> name >> birthday >> age;          //将获取字符串和整数
    qDebug() << name << birthday << age;
    file.close ();
}

9.3 目录操作与文件系统
QDir类具有存取目录结构和内容的能力,使用它可以操作目录,存取目录或文件信息、操作底层文件系统,而且还可以存取Qt的资源文件。
Qt使用“/”作为通用的目录分割符合URL路径分隔符。如果在程序中使用“/”作为目录分隔符,Qt会将其自动转换为符合底层操作系统的分隔符(如Linux使用“/”,Windows
使用“\”)。
QDir可以使用相对路径或绝对路径指向一个文件。isRelative()和isAbsolute()函数可以判断QDir对象使用的是相对路径还是绝对路径。如果需要讲一个相对路径转换为绝
对路径,则使用makeAbsolute()函数。
目录的路径可以通过path()函数返回,通过setPath()函数设置新路径。绝对路径使用absolutePath()返回,目录名可以使用dirName()获得,它通常返回绝对路径中的最后
一个元素,如果QDir指向当前目录,则返回“.”。目录的路径可以通过cd()和cdUp()改变。可以使用mkdir()创建目录,rename()改变目录名。
判断目录是否存在可以使用exists(),目录的属性可以使用isReadable()、isAbsolute()、isRelative()和isRoot()来获取。目录下的很多条目,包括文件、目录和符号链接,
总的条目数可以使用count()来统计。entryList()返回目录下所有条目组成的字符串链表。文件可以使用remove()函数删除,删除目录用rmdir()。

9.3.1 文件大小及路径获取实例

#include <QCoreApplication>
#include <QStringList>
#include <QDir>
#include <QDebug>
 
 
qint64 du(const QString &path)
{
    QDir dir(path);
    qint64 size = 0;
    foreach(QFileInfo fileinfo, dir.entryInfoList (QDir::Files))
    {
        size += fileinfo.size ();
    }
    /*返回目录下所有条目组成的字符串链表*/
    foreach(QString subdir, dir.entryList (QDir::Dirs | QDir::NoDotAndDotDot))
    {
        size += du(path + QDir::separator () + subdir);
    }
 
 
    char unit = 'B';
    qint64 cursize = size;
    if(cursize > 1024)
    {
        cursize /= 1024;
        unit = 'K';
        if(cursize > 1024)
        {
            cursize /= 1024;
            unit = 'M';
            if(cursize > 1024)
               {
                cursize /= 1024;
                unit = 'G';
            }
        }
    }
    qDebug() << cursize << unit << "\t" << qPrintable(path) << endl;
    return size;
}
/*
 * arguments()返回命令行参数
*/
int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);
 
 
    QStringList args = a.arguments ();
    QString path;
    if(args.count () > 1)
    {
        path = args[1];
    }
    else
    {
        path = QDir::currentPath ();
    }
    qDebug() << path << endl;
    du(path);
 
 
    return a.exec ();
}

9.3.2 文件系统浏览实例
文件系统的浏览是目录操作的一个常用功能。这里通过实现一个能够显示所有文件的文件系统的浏览功能,介绍如何使用QDir类显示文件系统目录及用过滤方式显示
文件列表的方法。

QDir的entryInfoList()方法是按照某种过滤方式获得目录下的文件列表。
QFileInfoList QDir::entryInfoList
(
     const QStringList &nameFilters,     //此参数指定了文件名的过滤方式,如“*”,“.tar.gz”
     Filters filters = NoFilters,               //此参数指定了文件属性的过滤方式,如目录、文件、读写属性等
     SortFlags sort = NoSort                //此参数指定了列表的排序情况
) const

QDir::Filter定义的过滤方式

过滤方式 作用描述
QDir::Dirs 按照过滤方式列出所有目录
QDir::AllDirs 列出所有目录,不考虑过滤方式
QDir::Files
只列出文件
QDir::Drives
列出磁盘驱动器(UNIX系统无效)
QDir::NoSymLinks
不列出符号链接(对不支持符号链接的操作系统无效)
QDir::NoDotAndDotDot
不列出“.”和“..”
QDir::AllEntries
列出目录、文件和磁盘驱动器。相当于Dirs|Files|Drives
QDir::Readable
列出所有具有“读”属性的文件和目录
QDir::Writable
列出所有具有“写”属性的文件和目录
QDir::Executable 列出所有具有“执行”属性的文件和目录
QDir::Modified
只列出被修改过的文件(UNIX系统生效)
QDir:::Hidden 列出隐藏文件(在UNIX系统下,隐藏文件的文件名以“.”开始)
QDir::System
列出系统文件(在UNIX系统下只FIFO、套接字和设备文件)
QDir::CaseSensitive
文件系统如果区分文件名大小写,则按大小写方式进行过滤

QDir::SortFlag定义了一系列排序方式

排序方式 作用描述
QDir::Name 按名称排序
QDir::Time
按时间排序(修改时间)
QDir::Size 按文件大小排序
QDir::Type 按文件类型排序
QDir::Unsorted 不排序
QDir::DirsFirst
目录优先排序
QDir::DirsLast
目录最后排序
QDir::Reversed 反序
QDir::IgnoreCase 忽略大小写方式排序
QDir::LocaleAware 使用当前本地排序方式进行排序


fileview.h

#ifndef FILEVIEW
#define FILEVIEW
 
 
#include <QDialog>
#include <QLineEdit>
#include <QDir>
#include <QLineEdit>
#include <QListWidget>
#include <QListWidgetItem>
#include <QFileInfoList>
#include <QVBoxLayout>
 
 
class FileView : public QDialog
{
    Q_OBJECT
public:
    FileView(QWidget *parent = 0, Qt::WindowFlags f = 0);
    ~FileView();
    void showFileInfoList(QFileInfoList list);
public slots:
    void slotShow(QDir dir);
    void slotDirShow(QListWidgetItem *item);
 
 
private:
    QLineEdit *fileLineEdit;
    QListWidget *fileListWidget;
    QVBoxLayout *mainLayout;
};
 
#endif   //   FILEVIEW
fileview.cpp
#include "fileview.h"
#include <QStringList>
#include <QIcon>
 
 
FileView::FileView(QWidget *parent,Qt::WindowFlags f)
    : QDialog(parent,f)
{
    setWindowTitle (tr("File View"));
 
 
    fileLineEdit = new QLineEdit(tr("/"));
    fileListWidget = new QListWidget;
 
 
    mainLayout = new QVBoxLayout(this);
    mainLayout->addWidget (fileLineEdit);
    mainLayout->addWidget (fileListWidget);
 
 
    connect (fileLineEdit, SIGNAL(returnPressed()), this, SLOT(slotShow(QDir)));
    connect (fileListWidget, SIGNAL(itemDoubleClicked(QListWidgetItem*)), this, SLOT(slotDirShow(QListWidgetItem*)));
 
 
    QString root = "/";
    QDir rootDir(root);
    QStringList string;
    string << "*";
    QFileInfoList list = rootDir.entryInfoList (string);
    showFileInfoList(list);
}
 
 
FileView::~FileView ()
{
 
 
}
/*
 * 显示dir下的所有文件
*/
void FileView::slotShow (QDir dir)
{
    QStringList string;
    string << "*";
    QFileInfoList list = dir.entryInfoList (string, QDir::AllEntries, QDir::DirsFirst);
    showFileInfoList (list);
}
/*
 * 根据用户的选择显示下一级目录的所有文件
*/
void FileView::slotDirShow (QListWidgetItem *item)
{
    QString str = item->text ();                //将下一级的目录保存在str中
    QDir dir;                                   //定义一个QDir对象
    dir.setPath (fileLineEdit->text ());        //设置QDir对象的路径为当前目录路径
    dir.cd (str);                               //根据下一级目录名重新设置QDir对象的路径
    fileLineEdit->setText (dir.absolutePath ());//刷新显示当前的目录路径
    slotShow(dir);                              //显示当前目录下的所有文件
}
/*
 * 用户可以双击浏览器中显示的目录进入下一级目录,或单击".."返回上一级目录,
 * 顶部的编辑框显示当前所在的目录路径,列表中显示当前该目录下的所有文件
 *
 *  for(unsigned int i = 0; i < list.count (); i++){...}:一次从QFilInfoList对象中取出所有项
 * 按目录和文件两种方式加入列表控件中。
*/
void FileView::showFileInfoList (QFileInfoList list)
{
    fileListWidget->clear ();   //清空列表控件
    for(unsigned int i = 0; i < list.count (); i++)
    {
        QFileInfo temFileInfo = list.at (i);
        if(temFileInfo.isDir ())
        {
            QIcon icon("dir.png");
            QString filename = temFileInfo.fileName ();
            QListWidgetItem *temp = new QListWidgetItem(icon, filename);
            fileListWidget->addItem (temp);
        }
        else if(temFileInfo.isFile ())
        {
            QIcon icon("file.png");
            QString filename = temFileInfo.fileName ();
            QListWidgetItem *temp = new QListWidgetItem(icon, filename);
            fileListWidget->addItem (temp);
        }
    }
}
9.4 获取文件信息
QFileinfo类提供了对文本进行操作时获得的文件相关属性、包括文件名、文件大小、创建时间最后修改时间、最后访问时间及一些文件是否为目录、文件或符号链接
和读写属性等。
fileinfo.h

#ifndef DIALOG_H
#define DIALOG_H
 
 
#include <QDialog>
#include <QLabel>
#include <QPushButton>
#include <QLineEdit>
#include <QCheckBox>
 
 
class FileInfo : public QDialog
{
    Q_OBJECT
 
 
public:
    FileInfo(QWidget *parent = 0);
    ~FileInfo();
 
 
public slots:
    void slotFile();
    void slotGet();
 
 
private:
 
 
    QLabel *fileNameLabel;
    QLineEdit *fileNameLineEdit;
    QPushButton *fileBtn;
 
 
    QLabel *sizeLabel;
    QLineEdit *sizeLineEdit;
 
 
    QLabel *createTimeLabel;
    QLineEdit *createTimeLineEdit;
 
 
    QLabel *lastModfiledLabel;
    QLineEdit *lastModFiledLineEdit;
 
 
    QLabel *lastReadLabel;
    QLineEdit *lastReadLineEdit;
 
 
    QLabel *propertyLabel;
    QCheckBox *isDirCheckBox;
    QCheckBox *isFileCheckBox;
    QCheckBox *isSymLinkCheckBox;
    QCheckBox *isHiddenCheckBox;
    QCheckBox *isReadableCheckBox;
    QCheckBox *isWriteableCheckBox;
    QCheckBox *isExecutableCheckBox;
 
 
    QPushButton *getBtn;
};
 
#endif   //   DIALOG_H
fileinfo.cpp
#include "fileinfo.h"
#include <QGridLayout>
#include <QFileDialog>
#include <QDateTime>
 
 
FileInfo::FileInfo(QWidget *parent)
    : QDialog(parent)
{
    fileNameLabel = new QLabel(tr("文件名:"));
    fileNameLineEdit = new QLineEdit;
    fileBtn = new QPushButton(tr("文件"));
    sizeLabel = new QLabel(tr("大小:"));
    sizeLineEdit = new QLineEdit;
    createTimeLabel = new QLabel(tr("创建时间:"));
    createTimeLineEdit = new QLineEdit;
    lastModfiledLabel = new QLabel(tr("最后修改时间:"));
    lastModFiledLineEdit = new QLineEdit;
    lastReadLabel = new QLabel(tr("最后访问时间"));
    lastReadLineEdit = new QLineEdit;
 
 
    propertyLabel = new QLabel(tr("属性:"));
    isDirCheckBox = new QCheckBox(tr("目录"));
    isFileCheckBox = new QCheckBox(tr("文件"));
    isSymLinkCheckBox = new QCheckBox(tr("符号链接"));
    isHiddenCheckBox = new QCheckBox(tr("隐藏"));
    isReadableCheckBox = new QCheckBox(tr("读"));
    isWriteableCheckBox = new QCheckBox(tr("写"));
    isExecutableCheckBox = new QCheckBox(tr("执行"));
 
 
    getBtn = new QPushButton(tr("获取文件信息"));
 
 
    QGridLayout *gridLayout = new QGridLayout;
    gridLayout->addWidget (fileNameLabel, 0, 0);
    gridLayout->addWidget (fileNameLineEdit, 0, 1);
    gridLayout->addWidget (fileBtn, 0, 2);
    gridLayout->addWidget (sizeLabel, 1, 0);
    gridLayout->addWidget (sizeLineEdit, 1, 1);
    gridLayout->addWidget (createTimeLabel, 2, 0);
    gridLayout->addWidget (createTimeLineEdit, 2, 1);
    gridLayout->addWidget (lastModfiledLabel, 3, 0);
    gridLayout->addWidget (lastModFiledLineEdit, 3, 1);
    gridLayout->addWidget (lastReadLabel, 4, 0);
    gridLayout->addWidget (lastReadLineEdit, 4, 1);
 
 
    QHBoxLayout *layout1 = new QHBoxLayout;
    layout1->addWidget (propertyLabel);
 
 
    QHBoxLayout *layout2 = new QHBoxLayout;
    layout2->addWidget (isDirCheckBox);
    layout2->addWidget (isFileCheckBox);
    layout2->addWidget (isSymLinkCheckBox);
    layout2->addWidget (isHiddenCheckBox);
    layout2->addWidget (isReadableCheckBox);
    layout2->addWidget (isWriteableCheckBox);
    layout2->addWidget (isExecutableCheckBox);
 
 
    QHBoxLayout *layout3 = new QHBoxLayout;
    layout3->addWidget (getBtn);
 
 
    QVBoxLayout *mainLayout = new QVBoxLayout(this);
    mainLayout->addLayout (gridLayout);
    mainLayout->addLayout (layout1);
    mainLayout->addLayout (layout2);
    mainLayout->addLayout (layout3);
 
 
    connect (fileBtn, SIGNAL(clicked(bool)), this, SLOT(slotFile()));
    connect (getBtn, SIGNAL(clicked(bool)), this, SLOT(slotGet()));
}
 
 
FileInfo::~FileInfo()
{
 
 
}
 
 
void FileInfo::slotFile ()
{
    QString fileName = QFileDialog::getOpenFileName (this, "打开", ",", "files(*)");
    fileNameLineEdit->setText (fileName);
}
 
 
void FileInfo::slotGet ()
{
    QString file = fileNameLineEdit->text ();
    QFileInfo info(file);
 
 
    qint64 size = info.size ();
    QDateTime created = info.created ();
    QDateTime lastModfiled = info.lastModified ();
    QDateTime lastRead = info.lastRead ();
 
 
    bool isDir = info.isDir ();
    bool isFile = info.isFile ();
    bool isSymLink = info.isSymLink ();
    bool isHidden = info.isHidden ();
    bool isReadable = info.isReadable ();
    bool isWriteable = info.isWritable ();
    bool isExecutable = info.isExecutable ();
 
 
    sizeLineEdit->setText (QString::number (size));
    createTimeLineEdit->setText (created.toString());
    lastModFiledLineEdit->setText (lastModfiled.toString());
    lastReadLineEdit->setText (lastRead.toString());
 
 
    isDirCheckBox->setCheckState (isDir ? Qt::Checked : Qt::Unchecked);
    isFileCheckBox->setCheckState(isFile ? Qt::Checked : Qt::Unchecked);
    isSymLinkCheckBox->setCheckState(isSymLink ? Qt::Checked : Qt::Unchecked);
    isHiddenCheckBox->setCheckState(isHidden ? Qt::Checked : Qt::Unchecked);
    isReadableCheckBox->setCheckState(isReadable ? Qt::Checked : Qt::Unchecked);
    isWriteableCheckBox->setCheckState(isWriteable ? Qt::Checked:  Qt::Unchecked);
    isExecutableCheckBox->setCheckState(isExecutable ? Qt::Checked : Qt::Unchecked);
}

  • 1
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值