首页 新闻 论坛 群组 Blog 文档 下载 读书 Tag 网摘 搜索 .NET Java 游戏 视频 人才 外包 培训 数据库 书店 程序员
中国软件网
欢迎您:游客 | 登录 注册 帮助
  • C++监视文件夹怎么做? [已结贴,结贴人:cothly]
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    发表于:2008-04-23 15:38:06 楼主
    如果一个文件夹里的文件被修改了或是追加了, 文件夹的信息会改变吧, 怎么取得文件夹的信息 用来判断文件夹里的内容被改变了。
    50  修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • oo
    • 等级:
    发表于:2008-04-23 15:41:561楼 得分:30
    如果是在windows下:


    监视程序,它的用途主要是在后台监视系统中关键信息的改变,比如注册表的改变及硬盘上由于文件操作引起的改变等等。下面我们开始讨论如何编程实现这一监视功能。首先介绍几个重要的api函数:
      FindFirstChangeNotification( );
      FindNextChangeNotification( );
      WaitForSingleObject( );
      其中FindFirstChangeNotification(lpzpath,fwatchsubtree,fdwfilter)中的lpzpath表示要监视的路径名,fwatchsubtree判断是否查看子目录,fdwfilter为要监视的事件,函数执行成功后返回一个句柄。
      参数fdwfilter取值及其含义如下:
      FILE_NOTIFY_CHANGE_FILE_NAME  查看指定目录下任何文件名的改变
      FILE_NOTIFY_CHANGE_DIR_NAME  查看指定目录下任何目录名的改变
      FILE_NOTIFY_CHANGE_SIZE  查看指定目录下文件大小的改变
      FILE_NOTIFY_CHANGE_ATTRIBUTES  查看指定目录下文件属性的改变
      FindNextChangeNotification(hchange),hchange为FindFirstChangenNotification返回的句柄,其作用是请求系统在下次检测到相应改变时发出改变通知消息句柄。当函数成功返回后,应用程序可通过WaitForMultipleObjects或WaitfForSingleObject来等待发生改变的通知。 WaitForSingleObject(hchange,dwmilliseconds)中hchange为FindFirstChangeNotification 返回的句柄,dwmilliseconds为等待时间值,指定等待完成需要的时间,单位为毫秒。该值为-1时表示时间无限长。最好在结束监视程序之前先用FindCloseChangeNotification(hchange)来关闭句柄。
      下面给出一个简单的实例,其功能就是监视c:\pwin98目录下是否有文件发生变化。一旦有重命名、创建或删除情况发生时,通过Edit控件给出提示。
            DWORD dwWaitStatus;
      HANDLE dwChangeHandle; //返回通知的句柄
      dwChangeHandle=FindFirstChangeNotification(
      “C:\\PWIN98”,false,FILE_NOTIFY_CHANGE_FILE_NAME); //设置返回通知的句柄
      if(dwChangeHandle==INVALID_HANDLE_VALUE)
      //判断是否设置成功
        ExitProcess(GetLastError());
      while(true){ //设置循环,监视是否有
        dwWaitStatus=WaitForSingleObject(dwChangeHandle,-1); //通知返回
        if(dwWaitStatus==0){
          MessageBox(NULL,"Notification",“Something Changed”,MB_OK); //给出提示
             FindCloseChangeNotification(dwcChangeHandle); //关闭句柄
          exit(EXIT_SUCCESS); //退出程序
        }
      }
      此例说明如何监视硬盘中文件变化,对于注册表,则有函数RegNotifyChangeKeyValue()可以实现类似功能。
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    发表于:2008-04-23 16:57:392楼 得分:15
    C/C++ code
    ReadDirectoryChangesW ReadDirectoryChangesW函数,这个函数不仅能够监测到文件系统的变化,还能够返回详细的文件变动的信息,并且能够选择是使用同步方式检测还是异步方式监测,比较全面,但是这个函数的使用比较复杂,而且有一些需要注意的地方,把我这几天使用的心得记录一下吧,参考了MSDN以及老外的一些文档! 首先是ReadDirectoryChangesW这个函数只在WinNT中能够使用,是新加的一个API函数,所以在VC++中使用该函数的时候需要在stdafx.h的#include <afxwin.h>的前面添加 #define _WIN32_WINNT 0x0500,实现的时候应该这样 #if(_WIN32_WINNT >= 0x0400) WINBASEAPI BOOL WINAPI ReadDirectoryChangesW( HANDLE hDirectory, LPVOID lpBuffer, DWORD nBufferLength, BOOL bWatchSubtree, DWORD dwNotifyFilter, LPDWORD lpBytesReturned, LPOVERLAPPED lpOverlapped, LPOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine ); #endif /* _WIN32_WINNT >= 0x0400 */ WINBASEAPI 否则会出现编译错误的情况!delphi里使用的时候不用注意这些问题! 其次,在文件系统更新很快,很频繁的时候,这个函数会出现漏掉监控信息的情况,这个原因在MSDN里有提到,MSDN里是这么说的:当你第一次调用ReadDirectoryChangesW这个函数的时候,系统会分配一些缓存来存储文件变化信息,这些缓存与要监控的文件夹关联,直到他关闭,并且这些缓存的大小在其生存期间不会改变,调用该函数的时候,文件的变化信息不断添加到这些缓存中,如果缓存溢出,这些改变信息会丢失,函数返回error_notify_enum_dir的错误。老外写了个类,据说解决了这个问题,我没有测试过,大家可以自己去看看!http://www.codeproject.com/file/directorychangewatcher.asp
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    发表于:2008-04-23 17:02:123楼 得分:0
    C/C++ code
    msdn 查 Change Journals Change Journals An automatic backup application is one example of a program that must check for changes to the state of a volume to perform its task. The brute force method of checking for changes in directories or files is to scan the entire volume. However, this is often not an acceptable approach because of the decrease in system performance it would cause. Another method is for the application to register a directory notification (by calling the FindFirstChangeNotification or ReadDirectoryChangesW functions) for the directories to be backed up. This is more efficient than the first method, however, it requires that an application be running at all times. Also, if a large number of directories and files must be backed up, the amount of processing and memory overhead for such an application might also cause the operating system's performance to decrease. To avoid these disadvantages, the NTFS file system maintains a change journal in Microsoft® Windows® 2000 and later. When any change is made to a file or directory in a volume, the change journal for that volume is updated with a description of the change and the name of the file or directory. Change journals are also needed to recover file system indexing — for example after a computer or volume failure. The ability to recover indexing means the file system can avoid the time-consuming process of reindexing the entire volume in such cases. The following topics discuss change journals:
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    发表于:2008-04-24 00:02:034楼 得分:0
    挺有用的东东
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    发表于:2008-04-24 01:49:105楼 得分:5
    记录前一次文件被修改的时间, 然后查看文件被修改的时间, 比较.
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    发表于:2008-04-24 08:48:436楼 得分:0
    http://topic.csdn.net/u/20080313/15/b1c5bff0-4671-4bb9-b59c-e768f4167e38.html
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    发表于:2008-04-29 15:26:287楼 得分:0
    to OO:
    在用WaitForSingleObject的时候,当监视的文件夹下有个文件改动,比如a, 那么我的程序去读a会读不成功, 要在
    if(dwWaitStatus==0){
      sleep(1000);
      读文件;
    }
    不知道是为什么, 不sleep直接读会失败。
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    发表于:2008-05-01 00:34:438楼 得分:0
    不会,帮顶
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    发表于:2008-05-01 10:19:559楼 得分:0
    不明LZ在说什么
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    发表于:2008-05-01 10:49:3010楼 得分:0
    当监视的文件夹下有个文件改动,比如a, 那么我的程序去读a会读不成功
    ===========================
    因为你见识到改动的时候,文件正在被打开进行修改,file handle还没有释放所以无法打开。

    你sleep 1秒也不能保证在所有情况下都能够正常打开,如果正在修改的程序对file handle占用时间超过一秒,还是会失败的。
    修改 删除 举报 引用 回复

    网站简介广告服务网站地图帮助联系方式诚聘英才English 问题报告
    北京创新乐知广告有限公司 版权所有 京 ICP 证 070598 号
    世纪乐知(北京)网络技术有限公司 提供技术支持
    Copyright © 2000-2008, CSDN.NET, All Rights Reserved