unity 用法 队列queue_Unity实践—多线程任务队列实现

本文介绍了Unity中如何实现多线程任务队列,包括串行与并发队列,使用Task和TaskScheduler进行任务调度。通过LimitedConcurrencyLevelTaskScheduler控制并发数,并结合Loom工具实现主线程同步。提供了创建和使用队列的代码示例,支持同步、异步执行以及主线程同步执行。
摘要由CSDN通过智能技术生成

Unity 已可使用 Thread、Task 等处理多线程任务,但缺少成熟的多线程任务队列工具,所以在此实现一个,代码已上传 Git 项目 GRUnityTools,可直接下载源码或通过 UPM 使用

实现目标串行与并发队列

队列是首要实现目标,且需要串行与并发两种队列,以覆盖不同需求

2. 同步与异步执行

因任务队列过多可能阻塞主线程,所以除同步执行外还需要多线程异步操作

3. 主线程同步

因为有多线程,但 Unity 部分操作只能在主线程执行,所以还需要线程同步到主线程

实现方式Task

Task 为当前 .Net 提供的实用性最高的多线程接口,可实现任务的监控与操纵

2. TaskScheduler

Task 专用调度器,可更便捷地实现 Task 队列调度

3. Loom

Loom 为网络上广为流传的 Unity 中调用主线程的工具类,目前找不到源码最原始地址,代码拷贝自知乎

实现过程

方案选择

最初即决定使用 Task 作为队列基本单位,但完全没有考虑 TaskScheduler。原计划手动实现一个调度器,负责保存传入的 Task 放入队列,可设置同步异步,根据设置实现对队列的不同操作。后来再研究微软官方文档时发现在其 Task 文档的示例中有一个 LimitedConcurrencyLevelTaskScheduler 的演示代码,直接通过 TaskScheduler 实现了可控并发数量的调度器,且当设置并发数为1时队列中的任务会逐一按顺序执行即产生了串行队列效果

TaskScheduler 有两种使用方式

方式一:为 TaskFactory 配置 TaskScheduler,通过 TaksFactory 使用配置的调度器启动 Task

//创建并发数32的调度器LimitedConcurrencyLevelTaskScheduler scheduler = new LimitedConcurrencyLevelTaskScheduler(32);

//方式1TaskFactory factory = new TaskFactory(scheduler);

factory.StartNew(()=>{

//执行任务});

方式二:直接使用 Task.Start(TaskFactory) 方法

//创建并发数1的调度器(此时即为串行队列效果)LimitedConcurrencyLevelTaskScheduler scheduler = new LimitedConcurrencyLevelTaskScheduler(1);

//声明一个 Task 对象Task task = new Task(()=>{

//任务});

//启动 Task 指定调度器task.Start(scheduler);

编写源码

创建名为 TaskQueue 的类,添加变量

//根据需求设置默认并发数private const int DefaultConcurrentCount = 32;

//线程锁private static object _lock = new object();

//默认静态串行队列对象private static TaskQueue _defaultSerial;

//默认静态并发队列对象private static TaskQueue _defaultConcurrent;

//持有的调度器private LimitedConcurrencyLevelTaskScheduler _scheduler;

//提供默认串行队列public static TaskQueue DefaultSerailQueue

{

get

{

if (_defaultSerial == null)

{

lock (_lock)

{

if (_defaultSerial == null)

{

_defaultSerial = new TaskQueue(1);

}

}

}

return _defaultSerial;

}

}

//提供默认并发队列public static TaskQueue DefaultConcurrentQueue

{

get

{

if (_defaultConcurrent == null)

{

lock (_lock)

{

if (_defaultConcurrent == null)

{

_defaultConcurrent = new TaskQueue(DefaultConcurrentCount);

}

}

}

return _defaultConcurrent;

}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值