c# 多线程排队队列实现的源码
- using System;
- using System.Threading;
- using System.Collections;
- using System.Collections.Generic;
- // 将线程同步事件封装在此类中,
- // 以便于将这些事件传递给 Consumer 和
- // Producer 类。
- public class SyncEvents
- {
- public SyncEvents()
- {
- // AutoResetEvent 用于“新项”事件,因为
- // 我们希望每当使用者线程响应此事件时,
- // 此事件就会自动重置。
- _newItemEvent = new AutoResetEvent(false);
- // ManualResetEvent 用于“退出”事件,因为
- // 我们希望发出此事件的信号时有多个线程响应。
- // 如果使用 AutoResetEvent,事件
- // 对象将在单个线程作出响应之后恢复为
- // 未发信号的状态,而其他线程将
- // 无法终止。
- _exitThreadEvent = new ManualResetEvent(false);
- // 这两个事件也放在一个 WaitHandle 数组中,以便
- // 使用者线程可以使用 WaitAny 方法
- // 阻塞这两个事件。
- _eventArray = new WaitHandle[2];
- _eventArray[0] = _newItemEvent;
- _eventArray[1] = _exitThreadEvent;
- }
- // 公共属性允许对事件进行安全访问。
- public EventWaitHandle ExitThreadEvent
- {
- get { return _exitThreadEvent; }
- }
- public EventWaitHandle NewItemEvent
- {
- get { return _newItemEvent; }
- }
- public WaitHandle[] EventArray
- {
- get { return _eventArray; }
- }
- private EventWaitHandle _newItemEvent;
- private EventWaitHandle _exitThreadEvent;
- private WaitHandle[] _eventArray;
- }
- // Producer 类(使用一个辅助线程)
- // 将项异步添加到队列中,共添加 20 个项。
- public class Producer
- {
- public Producer(Queue<int> q, SyncEvents e)
- {
- _queue = q;
- _syncEvents = e;
- }
- public void ThreadRun()
- {
- int count = 0;
- Random r = new Random();
- while (!_syncEvents.ExitThreadEvent.WaitOne(0, false))
- {
- lock (((ICollection)_queue).SyncRoot)
- {
- while (_queue.Count < 20)
- {
- _queue.Enqueue(r.Next(0, 100));
- _syncEvents.NewItemEvent.Set();
- count++;
- }
- }
- }
- Console.WriteLine("Producer thread: produced {0} items", count);
- }
- private Queue<int> _queue;
- private SyncEvents _syncEvents;
- }
- // Consumer 类通过自己的辅助线程使用队列
- // 中的项。Producer 类使用 NewItemEvent
- // 将新项通知 Consumer 类。
- public class Consumer
- {
- public Consumer(Queue<int> q, SyncEvents e)
- {
- _queue = q;
- _syncEvents = e;
- }
- public void ThreadRun()
- {
- int count = 0;
- while (WaitHandle.WaitAny(_syncEvents.EventArray) != 1)
- {
- lock (((ICollection)_queue).SyncRoot)
- {
- int item = _queue.Dequeue();
- }
- count++;
- }
- Console.WriteLine("Consumer Thread: consumed {0} items", count);
- }
- private Queue<int> _queue;
- private SyncEvents _syncEvents;
- }
- public class ThreadSyncSample
- {
- private static void ShowQueueContents(Queue<int> q)
- {
- // 对集合进行枚举本来就不是线程安全的,
- // 因此在整个枚举过程中锁定集合以防止
- // 使用者和制造者线程修改内容
- // 是绝对必要的。(此方法仅由
- // 主线程调用。)
- lock (((ICollection)q).SyncRoot)
- {
- foreach (int i in q)
- {
- Console.Write("{0} ", i);
- }
- }
- Console.WriteLine();
- }
- static void Main()
- {
- // 配置结构,该结构包含线程同步
- // 所需的事件信息。
- SyncEvents syncEvents = new SyncEvents();
- // 泛型队列集合用于存储要制造和使用的
- // 项。此例中使用的是“int”。
- Queue<int> queue = new Queue<int>();
- // 创建对象,一个用于制造项,一个用于
- // 使用项。将队列和线程同步事件传递给
- // 这两个对象。
- Console.WriteLine("Configuring worker threads...");
- Producer producer = new Producer(queue, syncEvents);
- Consumer consumer = new Consumer(queue, syncEvents);
- // 为制造者对象和使用者对象创建线程
- // 对象。此步骤并不创建或启动
- // 实际线程。
- Thread producerThread = new Thread(producer.ThreadRun);
- Thread consumerThread = new Thread(consumer.ThreadRun);
- // 创建和启动两个线程。
- Console.WriteLine("Launching producer and consumer threads...");
- producerThread.Start();
- consumerThread.Start();
- // 为制造者线程和使用者线程设置 10 秒的运行时间。
- // 使用主线程(执行此方法的线程)
- // 每隔 2.5 秒显示一次队列内容。
- for (int i = 0; i < 4; i++)
- {
- Thread.Sleep(2500);
- ShowQueueContents(queue);
- }
- // 向使用者线程和制造者线程发出终止信号。
- // 这两个线程都会响应,由于 ExitThreadEvent 是
- // 手动重置的事件,因此除非显式重置,否则将保持“设置”。
- Console.WriteLine("Signaling threads to terminate...");
- syncEvents.ExitThreadEvent.Set();
- // 使用 Join 阻塞主线程,首先阻塞到制造者线程
- // 终止,然后阻塞到使用者线程终止。
- Console.WriteLine("main thread waiting for threads to finish...");
- producerThread.Join();
- consumerThread.Join();
- }
- }
- namespace WindowsFormsApplication1
- {
- public partial class Form3 : Form
- {
- public Form3()
- {
- InitializeComponent();
- }
- public delegate void Delegate1();
- public delegate void Delegate2(DataTable dt);
- public void buttonFind_Click(object sender, EventArgs e)
- {
- Delegate1 d1 = new Delegate1(Find);
- d1.BeginInvoke(new AsyncCallback(AsyncCallback1), d1);
- }
- public void AsyncCallback1(IAsyncResult iAsyncResult)
- {
- Delegate1 d1 = (Delegate1)iAsyncResult.AsyncState;
- d1.EndInvoke(iAsyncResult);
- }
- public void Find()
- {
- DataTable dt = new DataTable();
- dt.Columns.Add("name", typeof(string));
- dt.Columns.Add("age", typeof(int));
- AddRow(dt, "张三", 19);
- AddRow(dt, "张三", 19);
- AddRow(dt, "李四", 18);
- this.Invoke(new Delegate2(Bind2), new object[] { dt });
- }
- public void AddRow(DataTable dt, string name, int age)
- {
- DataRow dr = dt.NewRow();
- dr["name"] = name;
- dr["age"] = age;
- dt.Rows.Add(dr);
- }
- public void Bind2(DataTable dt)
- {
- this.dataGridView1.DataSource = dt;
- }
- }
- }
转载于:https://www.cnblogs.com/ywsoftware/archive/2013/05/31/3110500.html
c# 多线程排队队列实现的源码相关推荐
- 医院排队叫号分诊管理系统源码,医院系统源码
医院排队叫号分诊管理系统源码,医院系统源码 功能介绍 1.1 分诊管理端 1.1.1 科室管理 登录分诊管理客户端后,在主界面的菜单中点击[科室管理],进入科室管理界面. 输入条件点击[查询]按钮,可 ...
- Android多线程:深入分析 Handler机制源码(二)
前言 在Android开发的多线程应用场景中,Handler机制十分常用 接下来,深入分析 Handler机制的源码,希望加深理解 目录 1. Handler 机制简介 定义 一套 Android 消 ...
- 阻塞队列和ArrayBlockingQueue源码解析
什么是阻塞队列 当队列中为空时,从队列总获取元素的操作将被阻塞,当队列满时,向队列中添加元素的操作将被阻塞.试图从空的阻塞队列中获取元素的线程将会被阻塞,知道其它的线程往队列中插入新的元素.同样,试图 ...
- Java多线程——重入锁ReentrantLock源码阅读
上一章<AQS源码阅读>讲了AQS框架,这次讲讲它的应用类(注意不是子类实现,待会细讲). ReentrantLock,顾名思义重入锁,但什么是重入,这个锁到底是怎样的,我们来看看类的注解 ...
- 华为OD机试之打印机队列(Java源码)
打印机队列 题目描述 有5台打印机打印文件,每台打印机有自己的待打印队列. 因为打印的文件内容有轻重缓急之分,所以队列中的文件有1~10不同的代先级,其中 数字越大优先级越高 打印机会从自己的待打印队 ...
- 【多线程】ThreadPoolExecutor类万字源码解析(注解超级详细)
线程池 线程池初始化时是没有创建线程的,线程池里的线程的初始化与其他线程一样,但是在完成任务以后,该线程不会自行销毁,而是以挂起的状态返回到线程池.直到应用程序再次向线程池发出请求时,线程池里挂起的线 ...
- C++使用linked list(链表)实现circular queue(循环队列)(附完整源码)
使用linked lis实现circular queue node结构体定义 使用linked list(链表)实现circular queue(循环队列)算法的完整源码(定义,实现,main函数测试 ...
- 自己实现多线程的socket,socketserver源码剖析
1,IO多路复用 三种多路复用的机制:select.poll.epoll 用的多的两个:select和epoll 简单的说就是: 1,select和poll所有平台都支持,epoll只有linux支持 ...
- 【死链】JDK1.7中HashMap在多线程环境的并发问题源码分析
文章目录 一.HashMap在JDK1.7中的并发问题 二.死链如何产生? 三.如何解决HashMap并发问题 参考文献 一.HashMap在JDK1.7中的并发问题 在JDK1.7中的HashMap ...
最新文章
- 浅谈Java的Fork/Join并发框架
- android 工程中引入第三方JAR包后安装APK时老是提示找不到库文件?
- 49 MM配置-库存管理和实际库存-设置容差限制
- vue 水平居中_小心!你弹琴的坐姿暴露了你演奏的水平!
- dubbo配置文件xml校验报错
- 马斯克点赞中国新能源汽车产业,特斯拉加快中国超级充电网络布局
- Eclipse启动Web项目 Tomcat中webapps中没有项目文件夹
- 如何列出所有用户的所有cron作业?
- 秒秒钟解决打开ps图片显示无法完成请求,因为程序错误
- springboot中日志使用
- 【微信小程序】微信支付
- 用户、巨头、计算平台,最终都是“社交”的傀儡?
- Python 人工智能:16~20
- 【ReView】 学习日志 from18/11/24 to 19/7/10
- PWN入门(2)利用缓冲区溢出绕过登录和第一个PwnTools脚本
- html投影电脑,投影仪怎么连接笔记本电脑
- 日语二级语法汇总(part8/16)
- linux下安装codeblocks及写完程序之后编译成功但无法运行的原因
- 用HTML+CSS+JavaScript教你如何制作浪漫的表白网站(程序员表白必备)
- Unity编辑器开发(三):实战、开发一个AB包编辑器工具
热门文章
- 我们从2021谷歌I/O大会给的谜题中发现了隐藏信息
- MySql模糊查询中特殊字符处理
- [译]Node v5.0.0 (Stable)
- Web模板引擎—Mustache
- [怪谈]唯有数学不会因时代的变迁而没落
- [物理学与PDEs]第2章习题参考解答
- Onenote 2010 多PC端笔记同步
- 百度“既盗版又盗链”,不但是音乐公司的害虫,也是音乐网站的害虫
- .NET新手系列(八)
- Tungsten Fabric SDN — Netronome Agilio SmartNIC vRouter