可指定并行度的任务调度器

https://social.msdn.microsoft.com/Forums/zh-CN/b02ba3b4-539b-46b7-af6b-a5ca3a61a309/task?forum=visualcshartzhchs

/// <summary>
/// 指定最大并行度的任务调度器
/// </summary>
public class SpecifyDegreeOfParallelismTaskScheduler : TaskScheduler
{
/// <summary>
/// 信号量锁
/// </summary>
private static System.Threading.SemaphoreSlim _lock = new System.Threading.SemaphoreSlim(1); /// <summary>
/// 当前线程是否正在处理任务
/// </summary>
[ThreadStatic]
private static bool _currentThreadIsProcessingItems; /// <summary>
/// 执行的任务队列
/// </summary>
private readonly LinkedList<Task> _tasks = new LinkedList<Task>(); /// <summary>
/// 指定的最大并行度
/// </summary>
private readonly int _maxDegressOfParallelism; /// <summary>
///当前调度器中正在执行的任务数
/// </summary>
private int _runingTasks = 0; /// <summary>
/// 指示此调度器能够支持的最大并发级别。
/// </summary>
public override int MaximumConcurrencyLevel { get { return this._maxDegressOfParallelism; } } /// <summary>
/// 初始化一个可指定最大并行度的任务调度器
/// </summary>
/// <param name="maxDegreeOfParallelism">最大并行度</param>
public SpecifyDegreeOfParallelismTaskScheduler(int maxDegreeOfParallelism)
{
if (maxDegreeOfParallelism < 1)
throw new ArgumentOutOfRangeException("maxDegreeOfParallelism至少为1");
this._maxDegressOfParallelism = maxDegreeOfParallelism;
} /// <summary>
/// 将Task排队到调度器中
/// </summary>
/// <param name="task">要排队的任务</param>
protected override void QueueTask(Task task)
{
_lock.Wait();
try
{
this._tasks.AddLast(task);
if (this._runingTasks < this._maxDegressOfParallelism)
{
++this._runingTasks;
ConsumeTaskOfPending();
}
}
finally
{
_lock.Release();
}
} /// <summary>
/// 尝试在当前线程上执行指定的任务
/// </summary>
/// <param name="task">被执行的任务</param>
/// <param name="taskWasPreviouslyQueued">指定的任务之前是否已经排队</param>
/// <returns>是否能在当前线程执行此任务</returns>
protected override bool TryExecuteTaskInline(Task task, bool taskWasPreviouslyQueued)
{
//如果当前前程没有正在处理项目,无法内联
if (!_currentThreadIsProcessingItems)
return false; //如果任务之前已经被排队,将其从队列中删除
if (taskWasPreviouslyQueued)
TryDequeue(task);
return base.TryExecuteTask(task);
} /// <summary>
/// 消费队列中等待的任务
/// </summary>
private void ConsumeTaskOfPending()
{
ThreadPool.UnsafeQueueUserWorkItem(p =>
{
_currentThreadIsProcessingItems = true;
try
{
while (true)
{
Task item;
_lock.Wait();
try
{
if (this._tasks.Count == 0)
{
--this._runingTasks;
break;
}
item = this._tasks.First.Value;
this._tasks.RemoveFirst();
}
finally
{
_lock.Release();
}
base.TryExecuteTask(item);
}
}
finally
{
_currentThreadIsProcessingItems = false;
}
}, null);
} /// <summary>
/// 尝试将任务从队列移除
/// </summary>
/// <param name="task">要移除的任务</param>
/// <returns>是否成功将任务从队列中移除</returns>
protected override bool TryDequeue(Task task)
{
_lock.Wait();
try
{
return this._tasks.Remove(task);
}
finally
{
_lock.Release();
}
} /// <summary>
/// 获取当前调度器中已调度任务序列
/// </summary>
/// <returns>可遍历已调度任务序列</returns>
protected override IEnumerable<Task> GetScheduledTasks()
{
_lock.Wait();
try
{
return this._tasks.ToArray();
}
finally
{
_lock.Release();
}
} }

C# 可指定并行度任务调度器的更多相关文章

  1. TaskScheduler一个.NET版任务调度器

    TaskScheduler是一个.net版的任务调度器.概念少,简单易用. 支持SimpleTrigger触发器,指定固定时间间隔和执行次数: 支持CronTrigger触发器,用强大的Cron表达式 ...

  2. Windows:任务调度器

    Windows 服务器系列: Windows:查看IP地址,IP地址对应的机器名,占用的端口,以及占用该端口的应用程 Windows:使用Dos命令管理服务(Services) Windows:任务调 ...

  3. [原创]php任务调度器 hellogerard/jobby

    目录 简介 安装 标准使用 选项 项目实践 简介 一个强大的php层面上的定时任务调度器, 无需修改系统层面的crontab 实际中, php 结合 crontab 来实现定时任务是一种经得住考验的实 ...

  4. 企业级任务调度框架Quartz(6) 任务调度器(Scheduler)

    前序:      我们已经在前面的内容能里看到了,我们用 Scheduler 来管理我们的 Job:创建并关联触发器以使 Job 能被触发执行:以及如可选择 calendar 为给定的时程安排提供更多 ...

  5. 2. SOFAJRaft源码分析—JRaft的定时任务调度器是怎么做的?

    看完这个实现之后,感觉还是要多看源码,多研究.其实JRaft的定时任务调度器是基于Netty的时间轮来做的,如果没有看过Netty的源码,很可能并不知道时间轮算法,也就很难想到要去使用这么优秀的定时调 ...

  6. 在springboot项目中引入quartz任务调度器。

    quartz是一个非常强大的任务调度器.我们可能使用它来管理我们的项目,常见的是做业绩统计等等.当然它的功能远不止这些.我们在这里不介绍quartz的原理,下面讲讲如何在springboot中使用qu ...

  7. 开源基于docker的任务调度器pipeline,比`quartzs` 更强大的分布式任务调度器

    pipeline 分布式任务调度器 目标: 基于docker的布式任务调度器, 比quartzs,xxl-job 更强大的分布式任务调度器. 可以将要执行的任务打包为docker镜像,或者选择已有镜像 ...

  8. C#TaskScheduler 任务调度器的原理

    什么是TaskScheduler? SynchronizationContext是对"调度程序(scheduler)"的通用抽象.个别框架会有自己的抽象调度程序,比如System. ...

  9. 21 BasicTaskScheduler基本任务调度器(一)——Live555源码阅读(一)任务调度相关类

    21_BasicTaskScheduler基本任务调度器(一)——Live555源码阅读(一)任务调度相关类 BasicTaskScheduler基本任务调度器 BasicTaskScheduler基 ...

随机推荐

  1. 自闭的D7

    先是一道**题然后我死了啊. A: 哇人人都会我不会系列. 我们可以运用逆向思维啊,把它转化成若干个人从点1进来, 然后我们考虑深度 dep,用 num[dep] 表示深度大于等于这个点的有多少个, ...

  2. Python学习之旅(七)

    Python基础知识(6):基本数据类型之列表 在Python中,最基本的数据结构是序列.序列中的每个元素被分配一个序号——即元素的位置,也称为索引.第一个索引从0开始,如果要从右边开始,序列中的最后 ...

  3. ERP项目实施记录09

    今天报价软件测试版本出来了,可看上去不怎么像是一款报价的软件,整个界面上都没有"报价"相关的字眼: 软件标题就不说了,反正影响不大,就当没看见,可左边这一大片菜单里也找不到和报价有 ...

  4. java awt 中文乱码 显示为 方块

    今天调试同学的五子棋程序,同学的界面是用awt写的,运行的时候,发现菜单栏中的中文都无法正常显示,而是变为了一个个方框, 类似于这样:(图片来源于网络) 即使做了字体设置,比如设置为宋体,也还是无法正 ...

  5. linux 系统下apache 找不到apxs 文件

    yum install httpd-devel

  6. 25个常用PowerShell命令总结

    尽管Windows PowerShell已经出现一段时间了,习惯命令行的管理员可能对了解PowerShell功能的基础很感兴趣. 下面我们看看能由Windows PowerShell完成的最常见的25 ...

  7. vue computed的执行问题

    1.在new Vue()的时候,vue\src\core\instance\index.js里面的_init()初始化各个功能 function Vue (options) { if (process ...

  8. xargs实例

    1. 当你使用rm命令去删除很多的文件时,你可能会得到错误信息:“/bin/rm Argument list too long – Linux”.这时可以用xargs来避免这个问题 find ~ -n ...

  9. HashMap出现Hash DOS攻击的问题

    随着RESTful风格的接口普及,程序员默认都会使用json作为数据传递的方式.json格式的数据冗余少,兼容性高,从提出到现在已被广泛的使用,可以说成为了Web的一种标准.无论我们服务端使用什么语言 ...

  10. 树莓派3 之 USB摄像头安装和使用

    需求 如果你想在树莓上拍照或者录影,你可以安装树莓派的摄像头(有点贵).如果你不想要为摄像头模块花费额外的金钱,那有另外一个方法,就是你常见的USB 摄像头.你可能已经在PC上安装过了.我买的如图的这 ...