我想知道是否可以设置从线程池中获得的线程的处理器亲和性。更具体地说,线程是通过使用TimerQueue API获得的,我用它来实现周期性任务。
作为附注:我发现TimerQueues是实现周期性任务的最简单的方法,但是由于这些任务通常是长时间的任务,使用专用线程来实现这个目的是否更合适呢?此外,预计需要使用诸如信号量和互斥量之类的同步原语来同步各种周期性任务。池化线程是否适用于这些线程?
谢谢!
EDIT1:正如Leo所指出的,上述问题实际上只是两个松散相关的问题。第一个问题与池化线程的处理器亲和性有关。第二个问题是,当涉及到同步对象时,从TimerQueue应用编程接口获得的池化线程的行为是否与手动创建的线程相同。我将把第二个问题移到另一个主题。
发布于 2010-11-24 22:56:56
如果执行此操作,请确保在每次将线程释放回池时将其恢复到原来的状态。由于您不拥有这些线程和其他使用它们的代码,因此可能会有其他要求/假设。
你确定你真的需要这样做吗?很少需要设置处理器亲和性。(我不认为在我写的任何东西中都需要这样做。)
BK1E线程亲和性可能意味着两个完全不同的东西。(感谢BK1E对我最初回答的评论指出了这一点。我还没有意识到我自己。)
从你的问题来看,你可能把#1和#2搞混了。,当你的回调函数运行时,线程本身不会改变。当线程运行时,它可能会在CPU之间跳转,但这是正常的,您不必担心(除非在非常特殊的情况下)。
Mutexes、信号量等并不关心线程是否在CPU之间跳转。
如果线程池多次执行回调,通常不能保证每次都使用相同的线程(具体取决于线程池的使用方式)。也就是说,您的回调可以在线程之间跳转,但不能在运行过程中跳转;它可能只会在每次再次运行时更改线程。
一些同步对象会关心你的回调代码是否在一个线程上运行,然后,仍然认为它持有这些对象上的锁,在另一个线程上再次运行。(第一个线程仍然持有锁,而不是第二个线程,尽管它取决于您使用的同步对象类型。有些人并不关心。)不过,这不是#1;这是#2,也不是您要使用SetThreadAffinityMask处理的东西。
例如,Mutexes (CreateMutex)归一个线程所有。如果你在线程A上获取了一个互斥锁,那么任何其他试图获取该互斥锁的线程都会被阻塞,直到你释放线程A上的互斥锁为止。(线程释放一个不属于它的互斥锁也是一个错误。)因此,如果您的回调获取了一个互斥锁,然后退出,然后在另一个线程上再次运行并从那里释放互斥锁,那就错了。
另一方面,事件(CreateEvent)并不关心哪些线程创建、发送信号或销毁它。你可以在一个线程上发信号通知一个事件,然后在另一个线程上重置它,这很好(实际上是正常的)。
在回调的两次单独运行之间持有同步对象的情况也很少见(这会导致死锁,尽管在某些情况下,您可能会合法地想要/做这样的事情)。但是,如果您创建(例如)一个单元线程的COM对象,那么您将只希望从一个特定的线程访问该对象。
发布于 2010-11-24 22:58:02
你不应该这样做,你只应该把这个线程用在手头的任务上,在它运行的处理器上。除了明显的效率低下之外,线程池可能会在您完成后立即销毁每个线程,并为您的下一项工作创建一个新线程。在实践中,亲和性掩码不会很快消失,但如果它们随机消失,调试起来就更难了。
https://stackoverflow.com/questions/4268019
复制相似问题