C/C++ Qt 监控文件状态变化
2023-02-18 16:46:21 时间
实现对特定文件的监控,Qt中提供了QFileSystemWatcher
调用这个接口可以快速实现监控功能,当有文件发生变化是自动触发并输出文件具体信息。
filesystem.h
#ifndef FILESYSTEM_H
#define FILESYSTEM_H
#include <QObject>
#include <QMap>
#include <QFileSystemWatcher>
class FileSystemWatcher : public QObject
{
Q_OBJECT
public:
static void addWatchPath(QString path);
public slots:
void directoryUpdated(const QString &path); // 目录更新时调用,path是监控的路径
void fileUpdated(const QString &path); // 文件被修改时调用,path是监控的路径
private:
explicit FileSystemWatcher(QObject *parent = 0);
private:
static FileSystemWatcher *m_pInstance; // 单例
QFileSystemWatcher *m_pSystemWatcher; // QFileSystemWatcher变量
QMap<QString, QStringList> m_currentContentsMap; // 当前每个监控的内容目录列表
};
#endif // FILESYSTEM_H
filesystem.cpp
#include <QDir>
#include <QFileInfo>
#include <qDebug>
#include "filesystem.h"
FileSystemWatcher* FileSystemWatcher::m_pInstance = NULL;
FileSystemWatcher::FileSystemWatcher(QObject *parent)
: QObject(parent)
{
}
// 监控文件或目录
void FileSystemWatcher::addWatchPath(QString path)
{
qDebug() << QString("Add to watch: %1").arg(path);
if (m_pInstance == NULL)
{
m_pInstance = new FileSystemWatcher();
m_pInstance->m_pSystemWatcher = new QFileSystemWatcher();
// 连接QFileSystemWatcher的directoryChanged和fileChanged信号到相应的槽
connect(m_pInstance->m_pSystemWatcher, SIGNAL(directoryChanged(QString)), m_pInstance, SLOT(directoryUpdated(QString)));
connect(m_pInstance->m_pSystemWatcher, SIGNAL(fileChanged(QString)), m_pInstance, SLOT(fileUpdated(QString)));
}
// 添加监控路径
m_pInstance->m_pSystemWatcher->addPath(path);
// 如果添加路径是一个目录,保存当前内容列表
QFileInfo file(path);
if (file.isDir())
{
const QDir dirw(path);
m_pInstance->m_currentContentsMap[path] = dirw.entryList(QDir::NoDotAndDotDot | QDir::AllDirs | QDir::Files, QDir::DirsFirst);
}
}
// 只要任何监控的目录更新(添加、删除、重命名),就会调用。
void FileSystemWatcher::directoryUpdated(const QString &path)
{
qDebug() << QString("Directory updated: %1").arg(path);
// 比较最新的内容和保存的内容找出区别(变化)
QStringList currEntryList = m_currentContentsMap[path];
const QDir dir(path);
QStringList newEntryList = dir.entryList(QDir::NoDotAndDotDot | QDir::AllDirs | QDir::Files, QDir::DirsFirst);
QSet<QString> newDirSet = QSet<QString>::fromList(newEntryList);
QSet<QString> currentDirSet = QSet<QString>::fromList(currEntryList);
// 添加了文件
QSet<QString> newFiles = newDirSet - currentDirSet;
QStringList newFile = newFiles.toList();
// 文件已被移除
QSet<QString> deletedFiles = currentDirSet - newDirSet;
QStringList deleteFile = deletedFiles.toList();
// 更新当前设置
m_currentContentsMap[path] = newEntryList;
if (!newFile.isEmpty() && !deleteFile.isEmpty())
{
// 文件/目录重命名
if ((newFile.count() == 1) && (deleteFile.count() == 1))
{
qDebug() << QString("File Renamed from %1 to %2").arg(deleteFile.first()).arg(newFile.first());
}
}
else
{
// 添加新文件/目录至Dir
if (!newFile.isEmpty())
{
qDebug() << "New Files/Dirs added: " << newFile;
foreach (QString file, newFile)
{
// 处理操作每个新文件....
}
}
// 从Dir中删除文件/目录
if (!deleteFile.isEmpty())
{
qDebug() << "Files/Dirs deleted: " << deleteFile;
foreach(QString file, deleteFile)
{
// 处理操作每个被删除的文件....
}
}
}
}
// 文件修改时调用
void FileSystemWatcher::fileUpdated(const QString &path)
{
QFileInfo file(path);
QString strPath = file.absolutePath();
QString strName = file.fileName();
qDebug() << QString("The file %1 at path %2 is updated").arg(strName).arg(strPath);
}
主调文件main.cpp
#include <QCoreApplication>
#include "filesystem.h"
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
FileSystemWatcher::addWatchPath("c://test");
return a.exec();
}
相关文章
- c++——构造函数和析构函数
- 深入浅出学习Linux
- git相关问题解析,你想要的都有?
- Go | 闭包的使用
- linux安装stable diffusion2.0完整教程-还不会安装sd2.0?一篇文章教会你AI绘画
- arm Linux中dma的cache管理
- 嵌入式:数据处理指令详解
- golang go-sql-driver gorm 数据库报错 bad connection
- linux 命令之 ls 命令详解
- git help 查看命令手册
- 【6】python生成数据曲线平滑处理——(Savitzky-Golay 滤波器、convolve滑动平均滤波)方法介绍,推荐玩强化学习的小伙伴收藏
- 数据挖掘机器学习[四]---汽车交易价格预测详细版本{嵌入式特征选择(XGBoots,LightGBM),模型调参(贪心、网格、贝叶斯调参)}
- 像go 一样 打造.NET 单文件应用程序的编译器项目bflat 发布 7.0版本
- 解决idea登录github出现的invalid authentication data 404 not found以及登录 token 失效
- 虹科方案|将以太网连接添加到Dell EMC PowerVault™ ML3 SAS库
- Linux运维常用shell脚本之系统管理实例
- Linux运维常用shell脚本之网络管理实例
- Java线程与Linux内核线程的映射关系
- PowerDesigner连接mysql逆向生成pdm
- oracle学习笔记(十六) PL/SQL 异常和goto语句