微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

等待WaitForMultipleObjects

我正在为我的FileWatcher类写一个unit testing。

FileWatcher派生自一个Thread类并使用WaitForMultipleObjects在其线程过程中等待两个句柄:

从FindFirstChangeNotification返回的句柄

一个事件的句柄,让我取消上面的等待。

所以基本上FileWatcher首先等待:文件改变或者我告诉它停止观看。

现在,当试图编写testing这个类的代码时,我需要等待它开始等待。

将vector声明为类成员

find缓冲区地址来创buildshell代码

Environment.GetFolderPath(Environment.SpecialFolder.System)和Environment.SystemDirectory for System32文件夹之间的区别

我在哪里可以获得编程反馈

如何设置QTableWidget高度在70以下

Peusdo代码

FileWatcher.Wait(INFINITE) ChangeFile() // Verify that FileWatcher works (with some other event - unimportant...)

问题是有一个竞争条件。 我需要首先确保FileWatcher已经开始等待(即它的线程现在被阻塞在WaitForMultipleObjects ),然后才能触发第二行中的文件更改。 我不想使用睡觉,因为,好吧,它似乎很乱,必将给我debugging时的问题。

我熟悉SignalObjectAndWait ,但它并不真正解决我的问题,因为我需要它“SignalObjectAndWaitOnMultipleObjects”…

有任何想法吗?

编辑

为了澄清一下,下面是FileWatcher类的简化版本:

// Inherit from this class,override OnChange,and call Start() to turn on monitoring. class FileChangeWatcher : public Utils::Thread { public: // File must exist before constructing this instance FileChangeWatcher(const std::string& filename); virtual int Run(); virtual void OnChange() = 0; };

它inheritance了Thread并实现了线程函数,看起来像这样(非常简化):

_changeEvent = ::FindFirstChangeNotificationW(wfn.c_str(),FALSE,FILE_NOTIFY_CHANGE_LAST_WRITE); HANDLE events[2] = { _changeEvent,m_hStopEvent }; DWORD hWaitDone = WAIT_OBJECT_0; while (hWaitDone == WAIT_OBJECT_0) { hWaitDone = ::WaitForMultipleObjects(2,events,INFINITE); if (hWaitDone == WAIT_OBJECT_0) OnChange(); else return Thread::THREAD_ABORTED; } return THREAD_FINISHED;

请注意,线程函数等待两个句柄,一个是更改通知,另一个是“停止线程”事件(从线程inheritance)。

现在testing这个类的代码如下所示:

class TestFileWatcher : public FileChangeWatcher { public: bool Changed; Event evtDone; TestFileWatcher(const std::string& fname) : FileChangeWatcher(fname) { Changed = false; } virtual void OnChange() { Changed = true; evtDone.Set(); } };

并从CPPUnittesting中调用

std::string tempFile = TempFilePath(); StringToFile("Hello,file",tempFile); TestFileWatcher tfw(tempFile); tfw.Start(); ::Sleep(100); // Ugly,but we have to wait for monitor to kick in in worker thread StringToFile("Modify me",tempFile); tfw.evtDone.Wait(INFINITE); CPPUNIT_ASSERT(tfw.Changed);

这个想法是摆脱中间的睡眠。

通过C ++检查以太网上的Windows计算机

将WriteFile()是primefaces,如果进程被终止,但系统继续运行?

memcached – 与C#asp.net应用程序一起使用

C的任务库?

如何从Windows上的c ++控制台应用程序打印UTF-8

没有比赛,您不必等待FileWatcher输入WaitForMultipleObjects 。 如果在调用函数之前执行更改,它将立即返回。

编辑:我现在可以看到比赛。 你为什么不移动下面的行

_changeEvent = ::FindFirstChangeNotificationW(/*...*/);

从线程函数到FileChangeWatcher的构造函数? 这样,您可以确定,在调用StringToFile函数时,文件已被监视。

您应该在观察者的构造函数调用FindFirstChangeNotification() ,并存储返回的线程函数的句柄。 这意味着您将从施工之初就抓住变化事件。

一旦你的线程已经开始,它只需要调用两个句柄的等待。 如果在线程启动之前发生了更改,则返回的FindFirstChangeNotification()返回的句柄将被发送,并且将会处理更改。 如果希望线程监视许多更改,则应该在处理每个通知后循环并调用FindNextChangeNotification() 。

相反,你可以使用Mutex吗? 在一个线程可以访问它所需要的资源之前,它必须锁定互斥锁并将其解锁为其他需要该资源的线程。

调用CreateEvent()来创建一个非信号事件。 当观察者线程进入其主循环(或其他)时,SetEvent()。 同时,在FileWatcher首先对事件的WaitForSingleObject(),然后一旦返回,WFMO就像你之前做的那样。

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

相关推荐