| 网站首页 | 业界新闻 | 小组 | 威客 | 人才 | 下载频道 | 博客 | 代码贴 | 在线编程 | 编程论坛
欢迎加入我们,一同切磋技术
用户名:   
 
密 码:  
共有 955 人关注过本帖
标题:事件的问题
只看楼主 加入收藏
bobo2185355
Rank: 2
等 级:论坛游民
帖 子:81
专家分:43
注 册:2010-4-11
结帖率:86.67%
收藏
已结贴  问题点数:20 回复次数:13 
事件的问题
举例:对一个功能模块建立了3个线程(a,b,c),EVENT中初始化为置位,那么a线程首先执行,但是在一个时间片内没有完成,他会被WINDOWS挂起,其他的线程也会被WaitForSingleObject所拒绝,只有当a现成再次分得时间片后,这段代码才能继续执行直到SetEvent,那么这段代码启不是被a现成独占的吗?请指点,如果描述中有错误请指出,毕竟新手上路.
还有个问题,如果这个代码执行一个循环,那么a线程在执行完第一遍循环之后时间片没到的话 他是继续执行循环还是一直等到时间片到被WINDOWS挂起为止
搜索更多相关主题的帖子: 时间 新手上路 时间 新手上路 时间 新手上路 
2010-10-18 00:40
bobo2185355
Rank: 2
等 级:论坛游民
帖 子:81
专家分:43
注 册:2010-4-11
收藏
得分:0 
问题的补充:今天看老罗的书看到12章了,对 事件 的问题是越看越糊涂,希望大家帮我下,为了阐述我的意思,我举一个可能不贴切的例子,我把事件比做一扇门,置位(为开门),复位(关门),WaitForSingleObject(把他比做看大门的,通知来访者能不能进入),SetEvent(比做开门命令),ResetEvent(比做关门命令).书里把事件看成WINDOWS内部标志,但是我看例题里面主线程用WaitForSingleObject检测事件的状态,子线程也用来检测事件状态,他们检测的是同一个标志吗?如果是同一个的话那就更不能理解了,子线程和主线程之间对事件的状态相互不影响吗?哎~~~这段内容我已经看了N遍了,看的我都快不认识中国字了,可能理解能里比较低,希望大家指点下
2010-10-18 01:10
cnfarer
Rank: 16Rank: 16Rank: 16Rank: 16
等 级:版主
威 望:179
帖 子:3330
专家分:21157
注 册:2010-1-19
收藏
得分:6 
这两个东西,在概念上还是有差别的。事件需要触发(系统或用户)。WaitForSingleObject只的程序执行时的一种机制。

★★★★★为人民服务★★★★★
2010-10-18 07:15
bobo2185355
Rank: 2
等 级:论坛游民
帖 子:81
专家分:43
注 册:2010-4-11
收藏
得分:0 
我也知道WINDOWS是事件驱动的,可是我觉得你只看了我的标题没看内容,所以你回答和没回答是一样的,不能给你分了
2010-10-18 08:35
ONEPROBLEM
Rank: 6Rank: 6
来 自:广西 南宁
等 级:贵宾
威 望:21
帖 子:1569
专家分:349
注 册:2008-7-11
收藏
得分:6 
在主线程和子线程中分别用WaitForSingleObjict来检测事件的状态,他们检测的是同一个标志。当然相互影响了。但是,可以把主线程和子线程看做是“同时”运行的。“开门”了,子线程在运算,主线程在发送!
而“关门”或,当然俩个都停下来了,否则,子线程都不工作了,主线程还在不停地发送原来的数据。这就不对了。

这是我的理解,不知道对不对。
2010-10-18 09:14
ONEPROBLEM
Rank: 6Rank: 6
来 自:广西 南宁
等 级:贵宾
威 望:21
帖 子:1569
专家分:349
注 册:2008-7-11
收藏
得分:0 
以下是引用bobo2185355在2010-10-18 00:40:04的发言:

举例:对一个功能模块建立了3个线程(a,b,c),EVENT中初始化为置位,那么a线程首先执行,但是在一个时间片内没有完成,他会被WINDOWS挂起,其他的线程也会被WaitForSingleObject所拒绝,只有当a现成再次分得时间片后,这段代码才能继续执行直到SetEvent,那么这段代码启不是被a现成独占的吗?请指点,如果描述中有错误请指出,毕竟新手上路.
还有个问题,如果这个代码执行一个循环,那么a线程在执行完第一遍循环之后时间片没到的话 他是继续执行循环还是一直等到时间片到被WINDOWS挂起为止
多线程同步执行,涉及到不同线程之间的“通信”和“协调”问题(个人理解的表述,可能不正确!),在某一时间片,某一线程对某一代码段的“独占性”,那是肯定的、也是必须的。
还有个问题,如果这个代码执行一个循环,那么a线程在执行完第一遍循环之后时间片没到的话 他是继续执行循环还是一直等到时间片到被WINDOWS挂起为止
这句话有问题,a线程的时间片没到,她就“静止”了!!
2010-10-18 09:24
bobo2185355
Rank: 2
等 级:论坛游民
帖 子:81
专家分:43
注 册:2010-4-11
收藏
得分:0 
我现在唯一不明白的地方就是,举例:3个线程(a,b,c)EVENT初始化为置位,自动复位,当线程a得到时间片执行代码的时候,如果在一个时间片内没有执行完,被WINDOWS挂起到就绪队列,但是线程,b,c,因为此时EVENT的状态是复位的状态,2个线程都被WaitForSingleObjict所拒绝,那么WINDOWS是不是根本就不会把b,c线程放到就绪队列,而是放到阻塞队列,那么就绪队列只有线程a,我晕 怎么又扯到操作系统了,有点晕了 我把书上的代码段复制过来 但是不能全部复制 只把线程函数复制了吧 希望能得到解释,我晕 连我自己都不知道在问什么了,应该是3个线程时间片的分配问题吧,就像我所描述的 b,c线程根本就不会被放到就绪队列里面
_Counter    proc    uses ebx esi edi,_lParam

        inc    dwThreads
        invoke    SetWindowText,hWinCount,addr szStop
        and    dwOption,not F_STOP

        .while    ! (dwOption & F_STOP)
            invoke    WaitForSingleObject,hEvent,INFINITE
            inc    dwCounter1
            mov    eax,dwCounter2
            inc    eax
            mov    dwCounter2,eax
            invoke    SetEvent,hEvent
        .endw
        dec    dwThreads
        invoke    SetWindowText,hWinCount,addr szStart
        ret

_Counter    endp
2010-10-18 11:00
bobo2185355
Rank: 2
等 级:论坛游民
帖 子:81
专家分:43
注 册:2010-4-11
收藏
得分:0 
对~~我好象就是 WINDOWS对3个线程是如何分配时间片的这个问题不明白,至于代码实现的功能不用解释 我知道
2010-10-18 11:19
zklhp
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
来 自:china
等 级:贵宾
威 望:254
帖 子:11485
专家分:33241
注 册:2007-7-10
收藏
得分:6 
诶 为嘛在汇编版讨论这个。。
2010-10-18 12:44
zklhp
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
来 自:china
等 级:贵宾
威 望:254
帖 子:11485
专家分:33241
注 册:2007-7-10
收藏
得分:0 
还有个问题,如果这个代码执行一个循环,那么a线程在执行完第一遍循环之后时间片没到的话 他是继续执行循环还是一直等到时间片到被WINDOWS挂起为止

应该是系统调度 线程 是进程的活跃部分 也就是 简单的说 作为一个线程 我只知道有我 不知道有别人。。

至于什么时候让我干活 什么时候不让我干活 不知道。。

windows核心编程如是说。。


前面讲过,有一个重要问题必须注意,即Wa i t F o r M u l t i p l e O b j e c t s是以原子操作方式运行的。当它检查内核对象的状态时,其他任何线程都无法背着对象改变它的状态。这可以防止出现死锁情况。试想,如果一个线程看到h A u t o R e s e t E v e n t 1已经得到通知并将事件重置为未通知状态,然后,另一个线程发现h A u t o R e s e t E v e n t 2已经得到通知并将该事件重置为未通知状态,那么这两个线程均将被冻结:一个线程将等待另一个线程已经得到的对象,另一个线程将等待该线程已经得到的对象。Wa i t F o r M u l t i p l e O b j e c t s能够确保这种情况永远不会发生。

这会产生一个非常有趣的问题,即如果多个线程等待单个内核对象,那么当该对象变成已通知状态时,系统究竟决定唤醒哪个线程呢? M i c r o s o f t对这个问题的正式回答是:“算法是公平的。”M i c r o s o f t不想使用系统使用的内部算法。它只是说该算法是公平的,这意味着如果多个线程正在等待,那么每当对象变为已通知状态时,每个线程都应该得到它自己的被唤醒的机会。

这意味着线程的优先级不起任何作用,即高优先级线程不一定得到该对象。这还意味着等待时间最长的线程不一定得到该对象。同时得到对象的线程有可能反复循环,并且再次得到该对象。但是,这对于其他线程来说是不公平的,因此该算法将设法防止这种情况的出现。但是这不一定做得到。

在实际操作中, M i c r o s o f t使用的算法是常用的“先进先出”的方案。等待了最长时间的线程将得到该对象。但是系统中将会执行一些操作,以便改变这个行为特性,使它不太容易预测。这就是为什么M i c r o s o f t没有明确说明该算法如何起作用的原因。操作之一是让线程暂停运行。如果一个线程等待一个对象,然后该线程暂停运行,那么系统就会忘记该线程正在等待该对象。这是一个特性,因为没有理由为一个暂停运行的线程进行调度。当后来该线程恢复运行时,系统将认为该线程刚刚开始等待该对象。

当调试一个进程时,只要到达一个断点,该进程中的所有线程均暂停运行。因此,调试一个进程会使“先进先出”的算法很难预测其结果,因为线程常常暂停运行,然后再恢复运行。


M i c r o s o f t对这个问题的正式回答是:“算法是公平的。”

我对这句的印象很深刻 这回答好。。 具体怎么调度的 可以看下wrk或泄漏的win源码或什么情景分析或自己逆向分析。。

其实我也不懂 希望有帮助

2010-10-18 12:50
快速回复:事件的问题
数据加载中...
 
   



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

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