返回顶部
首页 > 资讯 > 后端开发 > 其他教程 >C#线程池ThreadPool用法简介
  • 537
分享到

C#线程池ThreadPool用法简介

2024-04-02 19:04:59 537人浏览 薄情痞子
摘要

目录一、ThreadPool概述线程池使用起来很简单,但它有一些限制使用线程池线程的操作的情况包括二、方法三、设置和获取线程数方法四、将方法排入队列以便执行:QueueUserWor

一、ThreadPool概述

提供一个线程池,该线程池可用于执行任务、发送工作项、处理异步 I/O、代表其他线程等待以及处理计时器。

创建线程需要时间。如果有不同的小任务要完成,就可以事先创建许多线程/在应完成这些任务时发出请求。不需要自己创建这样一个列表。该列表由ThreadPool类托管。

这个类会在需要时增减池中线程的线程数,直到最大的线程数。

如果有更多的作业要处理,线程池中线程的个数也达到了极限,最新的作业就要排队,且必须等待线程完成其任务。

线程池使用起来很简单,但它有一些限制

  • 线程池中的所有线程都是后台线程。如果进程的所有前台线程都结束了,所有的后台线程 就会停止。不能把入池的线程改为前台线程。
  • 不能给入池的线程设置优先级或名称。
  • 对于COM对象,入池的所有线程都是多线程单元(multithreaded apartment, MTA)线程。许 多COM对象都需要单线程单元(single-threaded apartment, MTA)线程。
  • 入池的线程只能用于时间较短的任务。如果线程要一直运行(如Word的拼写检杳器线程), 就应使用Thread类创建一个线程.

使用线程池线程的操作的情况包括

  • 当您创建Task或Task对象以异步方式执行某项任务,默认情况下任务调度在线程池线程上运行的。
  • 异步计时器使用线程池。 线程池线程从System.Threading.Timer类执行回调,和从System.Timers.Timer类引发事件。
  • 当使用已注册的等待句柄时,系统线程监视等待句柄的状态。 等待操作完成后,从线程池的工作线程将执行相应的回调函数。
  • 当您调用QueueUserWorkItem方法进行排队,以在线程池线程上执行的方法。 为此,可将该方法传递WaitCallback委托。

二、方法

  • GetAvailableThreads(Int32, Int32):检索由 GetMaxThreads(Int32, Int32) 方法返回的最大线程池线程数和当前活动线程数之间的差值。
  • GetMaxThreads(Int32, Int32) :检索可以同时处于活动状态的线程池请求的数目。 所有大于此数目的请求将保持排队状态,直到线程池线程变为可用。
  • SetMaxThreads(Int32, Int32) :设置可以同时处于活动状态的线程池的请求数目。 所有大于此数目的请求将保持排队状态,直到线程池线程变为可用。
  • GetMinThreads(Int32, Int32):发出新的请求时,在切换到管理线程创建和销毁的算法之前检索线程池按需创建的线程的最小数量。
  • SetMinThreads(Int32, Int32):发出新的请求时,在切换到管理线程创建和销毁的算法之前设置线程池按需创建的线程的最小数量。
  • QueueUserWorkItem(WaitCallback, Object):将方法排入队列以便执行,并指定包含该方法所用数据的对象。 此方法在有线程池线程变得可用时执行。
  • RegisterWaitForSingleObject(WaitHandle, WaitOrTimerCallback, Object, Int32, Boolean) :注册一个等待 WaitHandle 的委托,并指定一个 32 位有符号整数来表示超时值(以毫秒为单位)。

三、设置和获取线程数方法

池中的最大线程数是可配置的。在双核CPU中,默认设置为1023 个工作线程和1000个I/O线程。也可以指定在创建线程池时应立即启动的最小线程数,以及线程池 中可用的最大线程数。

int i = 0;
int j = 0;
//前面是辅助(也就是所谓的工作者)线程,后面是I/O线程
ThreadPool.GetMaxThreads(out i, out j);
Console.WriteLine(i.ToString() + "   " + j.ToString()); //默认都是1000

//获取空闲线程,由于现在没有使用异步线程,所以为空
ThreadPool.GetAvailableThreads(out i, out j);
Console.WriteLine(i.ToString() + "   " + j.ToString()); //默认都是1000

四、将方法排入队列以便执行:QueueUserWorkItem(WaitCallback, Object)

将方法排入队列以便执行,并指定包含该方法所用数据的对象。 此方法在有线程池线程变得可用时执行。

public static bool QueueUserWorkItem (System.Threading.WaitCallback callBack, object state);

实例:

static void Main(string[] args)
 {
     Person p = new Person(1, "刘备");
     //启动工作者线程
     ThreadPool.QueueUserWorkItem(new WaitCallback(RunWorkerThread), p);
 }

static void RunWorkerThread(object obj)
 {
     Thread.Sleep(200);
     Console.WriteLine("线程池线程开始!");
     Person p = obj as Person;
     Console.WriteLine(p.Name);
 }


 public class Person
 {
     public Person(int id, string name) { Id = id; Name = name; }
     public int Id { get; set; }
     public string Name { get; set; }
 }

五、RegisterWaitForSingleObject 注册等待句柄

注册一个等待 WaitHandle 的委托,并指定一个数来表示超时值(以毫秒为单位)。

将指定的方法排队到线程池,当超时或者等待委托接收到信号时,辅助线程将执行此方法,即主线程控制辅助线程什么时候开始执行。

public static System.Threading.RegisteredWaitHandle RegisterWaitForSingleObject (System.Threading.WaitHandle waitObject, System.Threading.WaitOrTimerCallback callBack, object state, int millisecondsTimeOutInterval, bool executeOnlyOnce);

1、参数

  • waitObject:要注册的 WaitHandle。 使用 WaitHandle 而非 Mutex。
  • callBack :向 waitObject 参数发出信号时调用的 WaitOrTimerCallback 委托。
  • state:传递给委托的对象。
  • millisecondsTimeOutInterval:以毫秒为单位的超时。 
    如果为0(零),函数将测试对象的状态并立即返回。 如果为 -1,则函数的超时间隔永远不过期。表示间隔几秒执行回调方法,指当刚加入线程后,它是需要过了几秒后才会第一次执行回调方法。如果使用了wait.Set()方法使用立即执行回调函数而不需要等待。
  • executeOnlyOnce:如果为 true,表示在调用了委托后,线程将不再在 waitObject 参数上等待;如果为 false,表示每次完成等待操作后都重置计时器,直到注销等待。

2、返回

  • RegisteredWaitHandle:封装本机句柄的 RegisteredWaitHandle。
// TaskInfo contains data that will be passed to the callback method.
public class TaskInfo
{
    public RegisteredWaitHandle Handle = null;
    public string OtherInfo = "default";
}


public static void Main(string[] args)
{
    // 主线程使用AutoResetEvent来给已注册的等待句柄发信号, 此等待句柄执行回调方法
    AutoResetEvent ev = new AutoResetEvent(false);

    TaskInfo ti = new TaskInfo();
    ti.OtherInfo = "First task";
    // 该任务的TaskInfo包括RegisterWaitForSingleObject返回的已注册的等待句柄。这允许在对象被发出一次信号时终止等待(参见WaitProc)。
    ti.Handle = ThreadPool.RegisterWaitForSingleObject(
        ev,
        new WaitOrTimerCallback(WaitProc),
        ti,
        1000,
        false
    );

    // 主线程等待三秒,为了演示队列中的线程超时,然后发信号.
    Thread.Sleep(3100);
    Console.WriteLine("Main thread signals.");
    ev.Set();//发信号

    // 主线程休眠,这应该给回调方法执行的时间。如果注释掉这一行,程序通常会在ThreadPool线程执行之前结束。
    Thread.Sleep(1000);
    / /如果您自己启动一个线程,您可以通过调用thread . join来等待它结束。此选项在线程池线程中不可用。
}

//当注册的等待时间超时,或者WaitHandle(在本例中是AutoResetEvent)发出信号时,回调方法执行。WaitProc在事件第一次发出信号时注销WaitHandle。.
public static void WaitProc(object state, bool timedOut)
{
    TaskInfo ti = (TaskInfo)state;

    string cause = "TIMED OUT";
    if (!timedOut) //如果Timeout为false,表示接收到的信号后执行的
    {
        cause = "SIGNALED";
        //如果回调方法执行的话是因为WaitHandle触发信号的话,则用反注册等待句柄来取消回调方法将来的执行。
        if (ti.Handle != null)
            ti.Handle.Unregister(null);//
    }

    Console.WriteLine("WaitProc( {0} ) executes on thread {1}; cause = {2}.",
        ti.OtherInfo, Thread.CurrentThread.GetHashCode().ToString(), cause);//超时后执行的
}

结果如下:

WaitProc( First task ) executes on thread 7; cause = TIMED OUT.
WaitProc( First task ) executes on thread 7; cause = TIMED OUT.
WaitProc( First task ) executes on thread 7; cause = TIMED OUT.
Main thread signals.
WaitProc( First task ) executes on thread 7; cause = SIGNALED.

到此这篇关于C#线程池ThreadPool的文章就介绍到这了。希望对大家的学习有所帮助,也希望大家多多支持编程网。

--结束END--

本文标题: C#线程池ThreadPool用法简介

本文链接: https://lsjlt.com/news/150823.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

猜你喜欢
  • C#线程池ThreadPool用法简介
    目录一、ThreadPool概述线程池使用起来很简单,但它有一些限制使用线程池线程的操作的情况包括二、方法三、设置和获取线程数方法四、将方法排入队列以便执行:QueueUserWor...
    99+
    2024-04-02
  • C#多线程之线程池ThreadPool用法
    目录一、ThreadPool1、QueueUserWorkItem()2、GetMaxThreads()3、GetMinThreads()4、SetMaxThreads()和SetM...
    99+
    2024-04-02
  • C#多线程之线程池(ThreadPool)
    一、简介 前面介绍了平时用到的大多数的多线程的例子,但在实际开发中使用的线程往往是大量的和更为复杂的,这时,每次都创建线程、启动线程。从性能上来讲,这样做并不理想(因为每使用一个线程...
    99+
    2024-04-02
  • C#线程池ThreadPool怎么使用
    这篇文章主要讲解了“C#线程池ThreadPool怎么使用”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“C#线程池ThreadPool怎么使用”吧!一、ThreadPool概述提供一个线程池...
    99+
    2023-07-02
  • python线程池(threadpool
    最近碰到个问题,需要telnet登录上千台机器去取主机名;其中有用户名密码交互部分,有需要延迟的部分,大概一次登录一次到处理完要10s,1000台机器串行处理就需要1000×10s,差不多三个小时,这是很难受的事情; 之前用thread的...
    99+
    2023-01-31
    线程 python threadpool
  • python 线程池threadpool
    最近在做一个视频设备管理的项目,设备包括(摄像机,DVR,NVR等),包括设备信息补全,设备状态推送,设备流地址推送等,如果同时导入的设备数量较多,如果使用单线程进行设备检测,那么由于设备数量较多,会带来较大的延时,因此考虑多线程处理此问...
    99+
    2023-01-31
    线程 python threadpool
  • C#多线程之线程池ThreadPool详解
    一、ThreadPool概述 提供一个线程池,该线程池可用于执行任务、发送工作项、处理异步 I/O、代表其他线程等待以及处理计时器。 创建线程需要时间。如果有不同的小任务要完成,就可...
    99+
    2024-04-02
  • C++中线程池ThreadPool源码解析
    目录什么是线程什么是线程池线程池解决什么问题怎么用线程池总结什么是线程 线程是进程中的⼀个执⾏单元,负责当前进程中程序的执⾏,⼀个进程中⾄少有⼀个线程。⼀个进程中是可以有多个线程的,...
    99+
    2024-04-02
  • 浅谈python 线程池threadpool之实现
    首先介绍一下自己使用到的名词: 工作线程(worker):创建线程池时,按照指定的线程数量,创建工作线程,等待从任务队列中get任务; 任务(requests):即工作线程处理的任务,任务可能成千上万个,但...
    99+
    2022-06-04
    浅谈 线程 python
  • .NET 6线程池ThreadPool实现概述
    目录前言任务的调度基本调度单元IThreadPoolWorkItem 实现类的实例。Task全局队列本地队列偷窃机制Worker Thread 的生命周期管理线程注入实验.NET 5...
    99+
    2024-04-02
  • python线程池(threadpool)模块使用笔记详解
    最近在做一个视频设备管理的项目,设备包括(摄像机,DVR,NVR等),包括设备信息补全,设备状态推送,设备流地址推送等,如果同时导入的设备数量较多,如果使用单线程进行设备检测,那么由于设备数量较多,会带来较...
    99+
    2022-06-04
    线程 详解 模块
  • 通过Java讲解ThreadPool线程池的示例
    这篇文章主要为大家展示了通过Java讲解ThreadPool线程池的示例,内容简而易懂,条理清晰,希望能够帮助大家解决疑惑,下面让小编带大家一起来研究并学习一下“通过Java讲解ThreadPool线程池的示例”这篇文章吧。Java的特点有...
    99+
    2023-06-06
  • C#异步多线程ThreadPool怎么使用
    这篇文章主要讲解了“C#异步多线程ThreadPool怎么使用”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“C#异步多线程ThreadPool怎么使用”吧!启动线程池线程ThreadPool...
    99+
    2023-06-25
  • C#线程的简单介绍
    本篇内容介绍了“C#线程的简单介绍”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!C#线程是什么呢?在操作系统中一个进程至少要包含一个线程,然...
    99+
    2023-06-17
  • 一篇文章带你了解Java中ThreadPool线程池
    目录ThreadPool线程池的优势线程池的特点1 线程池的方法(1) newFixedThreadPool(2) newSingleThreadExecutor(3) newSch...
    99+
    2024-04-02
  • Linux C线程池简单实现实例
    Linux C线程池 三个文件 1 tpool.h typedef struct tpool_work { void (*routine)(void *); void ...
    99+
    2022-06-04
    线程 实例 简单
  • Dubbo框架线程池使用介绍
    目录1、Dubbo已有线程池2、自定义线程池1、Dubbo已有线程池 dubbo在使用时,都是通过创建真实的业务线程池进行操作的。目前已知的线程池模型有两个和java中的相互对应: ...
    99+
    2024-04-02
  • C++怎么实现一个简单的线程池
    本文小编为大家详细介绍“C++怎么实现一个简单的线程池”,内容详细,步骤清晰,细节处理妥当,希望这篇“C++怎么实现一个简单的线程池”文章能帮助大家解决疑惑,下面跟着小编的思路慢慢深入,一起来学习新知识吧。一、设计线程池应该包括保存线程的容...
    99+
    2023-06-30
  • Java线程池的简单使用方法实例教程
    目录线程池使用场景? Java线程池使用总结线程池使用场景? java中经常需要用到多线程来处理一些业务,我们非常不建议单纯使用继承Thread或者实现Runnable接口...
    99+
    2024-04-02
  • C++ 多线程编程中线程池的应用
    c++++ 多线程编程中使用线程池的好处包括:1)减少线程创建次数;2)负载均衡;3)避免资源争用。例如,通过使用线程池将图像转换任务分配给线程池,可以提高文件转换应用程序的转换速度。 ...
    99+
    2024-05-14
    多线程 线程池 c++ 标准库
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作