等待Task.Run(()=> semaphore.WaitOne())有什么问题吗?

标题说明了一切。 await Task.Run(() => semaphore.WaitOne());有什么问题await Task.Run(() => semaphore.WaitOne());System.Threading.Semaphore不是线程仿射的,所以我不认为会有问题。 我知道SemaphoreSlim类可用,但我需要做跨进程同步,而SemaphoreSlim不会那样做。

或者可以/我应该创建自己的自定义类型的WaitHandle吗?


如果你想在这里等待信号量的时候保持UI的响应,这可能是有道理的,但有一个问题:“信号量没有所有者”。 如果您在两个进程之间共享信号量,并且另一个进程崩溃而不调用Semaphore.Release()则共享资源的所有权将会丢失 。 剩下的过程可能无法再次获取它。

国际海事组织, Mutex语义在这里会更合适,但使用Mutex你需要线程亲和力。 也许,你可以获得互斥体,访问资源并在相同的线程上释放它:

await Task.Factory.StartNew(() => 
{
    mutex.WaitOne();
    try
    {
        // use the shared resource
    }
    finally
    {
        mutex.ReleaseMutex(); 
    }
}, TaskCreationOptions.LongRunnning);

如果这是不可能的(例如,因为您需要访问主UI线程上的共享资源),则可以使用专用线程来处理互斥锁。 这可以通过一个自定义的任务调度程序完成,例如Stephen Toub的带有numberOfThreads:1StaTaskScheduler numberOfThreads:1 (在这种情况下,帮助程序线程不必做STA):

using (var scheduler = new StaTaskScheduler(numberOfThreads: 1))
{
    await Task.Factory.StartNew(
        () => mutex.WaitOne(), 
        CancellationToken.None,
        TaskCreationOptions.None,
        scheduler);
    try
    {
        // use the shared resource on the UI thread
    }
    finally
    {
        Task.Factory.StartNew(
            () => mutex.ReleaseMutex(), 
            CancellationToken.None,
            TaskCreationOptions.None,
            scheduler).Wait();
    }
}

更新 ,如果你担心WinRT(即.NET的Windows应用商店应用)或Windows Phone,那么Task.Factory.StartNew w / TaskCreationOptions.LongRunning仍然存在,你可以使用它而不是new Thread()StaTaskScheduler或者当你需要一个具有亲和力的后台线程时,像我的ThreadWithSerialSyncContext

链接地址: http://www.djcxy.com/p/78689.html

上一篇: Is there anything wrong with await Task.Run(() => semaphore.WaitOne())?

下一篇: How to get numbers of online users using .NET Identity 2.0 in MVC 5