| 网站首页 | 业界新闻 | 小组 | 威客 | 人才 | 下载频道 | 博客 | 代码贴 | 在线编程 | 编程论坛
欢迎加入我们,一同切磋技术
用户名:   
 
密 码:  
共有 224 人关注过本帖
标题:filesystemwatcher 在 win11下信号多次触发的问题
只看楼主 加入收藏
Yio
Rank: 1
等 级:新手上路
帖 子:2
专家分:0
注 册:2024-12-26
收藏
 问题点数:0 回复次数:2 
filesystemwatcher 在 win11下信号多次触发的问题
我在win11下,使用qt5.10版本,想要实现 目录监视 的效果,我选择了filesystemwatcher
但是发现,会有情况出现大量信号触发的问题,我的大体代码如下:

我使用
connect(&folderWatcher, &QFileSystemWatcher::directoryChanged, [&](const QString &path){
        qDebug()<< "\n文件夹内容已修改 "<< path;
    });
目录发生改变,我只进行输出。

然后我目录结构为

share---|
        |---|
            |---aaa
                 |
                 |---test (空目录)
                 |---test1
                 |---test2
         
我将 share aaa test test1 test2 均加入监视,这样我就能监控下面的文件变化,但是程序启动后,
我如果删除其中目录,比如 test1 会提示 “文件夹访问被拒绝  需要提供管理员权限才能删除” (如果不启动程序,删除是正常的)
然后可能会删除失败。
但这只是个小问题,更大的问题是  如果我尝试删除 aaa 目录,我就会收到非常多的信号,因为我的终端有大量打印
都是重复的 “文件夹内容已修改  "C:/Users/sw020/Documents/share/aaa/test/"”,然后我必须停止程序才能停止打印。
因为 test 为空目录 ,所以我猜测与空目录有关? 然后我尝试只删除 test ,然后出现也有一些打印,但是很快就停止了,但是打印中的
path 值 ,不仅包含了 aaa 目录 也包含很多次 test  甚至也包含了 test1 和 test2。

所以有人明白这是为什么吗,为什么在win11下有的情况槽函数触发会有问题。
搜索更多相关主题的帖子: 信号 目录 test 删除 触发 
2024-12-26 09:34
Yio
Rank: 1
等 级:新手上路
帖 子:2
专家分:0
注 册:2024-12-26
收藏
得分:0 
2024-12-26 10:26
鸿蒙之灵
Rank: 4
来 自:异次元裂缝
等 级:贵宾
威 望:11
帖 子:129
专家分:244
注 册:2016-8-22
收藏
得分:0 
你的打印语句在此只能证明你的监视信号正常发出并且槽函数正常响应了,由于目录具有层级结构,故相关一次更新会出现很多的打印语句就不足为奇了;至于你说的需要权限才能删除,我觉得是你信号的用法有问题,你可以用下面的代码尝试一下;

程序代码:
    //这里添加你需要监视的路径,最好创建一个类,每一个需要监视的路径都是这个类的一个对象
    qDebug() << QString("添加监控目录: %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 xxxx::directoryUpdated(const QString &path)
{
    qDebug() << QString("目录更新: %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("文件重命名 %1 到 %2").arg(deleteFile.first()).arg(newFile.first());
        }
    }
    else
    {
        // 添加新文件/目录至Dir
        if (!newFile.isEmpty())
        {
           qDebug() << "新建文件或目录: " << newFile;

            foreach (QString file, newFile)
            {
                // 处理操作每个新文件....
            }
        }

        // 从Dir中删除文件/目录
        if (!deleteFile.isEmpty())
        {
            qDebug() << "删除文件或目录: " << deleteFile;

            foreach(QString file, deleteFile)
            {
                // 处理操作每个被删除的文件....
            }
        }
    }
}



程序代码:
//文件变化槽函数
void xxxx::fileUpdated(const QString &path)
{
    QFileInfo file(path);
    QString strPath = file.absolutePath();
    QString strName = file.fileName();

   qDebug() << QString("文件 %1 路径 %2 修改").arg(strName).arg(strPath);
}




[此贴子已经被作者于2025-1-25 09:23编辑过]


对待编程,要像对待情人一样
2025-01-25 09:01
快速回复:filesystemwatcher 在 win11下信号多次触发的问题
数据加载中...
 
   



关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.017914 second(s), 8 queries.
Copyright©2004-2025, BCCN.NET, All Rights Reserved