如何在 ThreadPool 上进行 Rx 回调 运行?
How to make the Rx callbacks run on the ThreadPool?
您希望下面的程序打印 False
吗?
using System;
using System.Threading;
using System.Reactive.Linq;
using System.Reactive.Concurrency;
public static class Program
{
public static void Main()
{
Observable
.Return(1)
.ObserveOn(ThreadPoolScheduler.Instance)
.Do(x => Console.WriteLine(Thread.CurrentThread.IsThreadPoolThread))
.Wait();
}
}
输出:
False
我的理解是 System.Threading
命名空间中的 ThreadPoolScheduler
is intended for scheduling work on the ThreadPool
, but apparently this is not what happening. Its name probably refers to some other thread pool, internal to Rx, and not to the actual ThreadPool
class。
我曾多次尝试在 ThreadPool
上强制回调到 运行,但没有成功。我尝试过的一些事情:
.ObserveOn(Scheduler.Default)
.ObserveOn(DefaultScheduler.Instance)
.ObserveOn(TaskPoolScheduler.Default)
.ObserveOn(new TaskPoolScheduler(Task.Factory))
.ObserveOn(new TaskPoolScheduler(new TaskFactory(TaskScheduler.Default)))
ThreadPoolScheduler.Instance.DisableOptimizations(); // At the start of the program
上面的最后一次尝试是在阅读 this question in Microsoft's forums. No matter what I've tried, the Thread.IsThreadPoolThread
属性 后不断返回 false
。
我是否应该编写自己的 IScheduler
实现以确保我的代码 运行 在 ThreadPool
上?对于这样一个微不足道的目标来说,这听起来像是一项非常重要的工作。
.NET 5.0.1,System.Reactive 5.0.0,C# 9
你分享的link竟然有解决办法:
var modScheduler = ThreadPoolScheduler.Instance.DisableOptimizations(new[] { typeof(ISchedulerLongRunning) });
Observable
.Return(1)
.ObserveOn(modScheduler)
.Select(_ => Thread.CurrentThread)
.Subscribe(t => Console.WriteLine(t.IsThreadPoolThread));
如果您查看 ThreadPoolScheduler
的源代码,您会发现所有工作都发送到线程池,ScheduleLongRunning
除外。如果您禁用该优化,那么所有工作都将发送到线程池。
您希望下面的程序打印 False
吗?
using System;
using System.Threading;
using System.Reactive.Linq;
using System.Reactive.Concurrency;
public static class Program
{
public static void Main()
{
Observable
.Return(1)
.ObserveOn(ThreadPoolScheduler.Instance)
.Do(x => Console.WriteLine(Thread.CurrentThread.IsThreadPoolThread))
.Wait();
}
}
输出:
False
我的理解是 System.Threading
命名空间中的 ThreadPoolScheduler
is intended for scheduling work on the ThreadPool
, but apparently this is not what happening. Its name probably refers to some other thread pool, internal to Rx, and not to the actual ThreadPool
class。
我曾多次尝试在 ThreadPool
上强制回调到 运行,但没有成功。我尝试过的一些事情:
.ObserveOn(Scheduler.Default)
.ObserveOn(DefaultScheduler.Instance)
.ObserveOn(TaskPoolScheduler.Default)
.ObserveOn(new TaskPoolScheduler(Task.Factory))
.ObserveOn(new TaskPoolScheduler(new TaskFactory(TaskScheduler.Default)))
ThreadPoolScheduler.Instance.DisableOptimizations(); // At the start of the program
上面的最后一次尝试是在阅读 this question in Microsoft's forums. No matter what I've tried, the Thread.IsThreadPoolThread
属性 后不断返回 false
。
我是否应该编写自己的 IScheduler
实现以确保我的代码 运行 在 ThreadPool
上?对于这样一个微不足道的目标来说,这听起来像是一项非常重要的工作。
.NET 5.0.1,System.Reactive 5.0.0,C# 9
你分享的link竟然有解决办法:
var modScheduler = ThreadPoolScheduler.Instance.DisableOptimizations(new[] { typeof(ISchedulerLongRunning) });
Observable
.Return(1)
.ObserveOn(modScheduler)
.Select(_ => Thread.CurrentThread)
.Subscribe(t => Console.WriteLine(t.IsThreadPoolThread));
如果您查看 ThreadPoolScheduler
的源代码,您会发现所有工作都发送到线程池,ScheduleLongRunning
除外。如果您禁用该优化,那么所有工作都将发送到线程池。