C# Winform 入门(14)之如何使用线程池

发布于:2025-04-08 ⋅ 阅读:(41) ⋅ 点赞:(0)

什么是线程?

首先我们要弄明白什么是线程,线程和线程池有啥区别?

C# 多线程应用(同步异步)_c# 异步线程-CSDN博客

 补充:ManualResetEvent 的使用

ManualResetEvent 是一种线程同步机制,用于控制一个或者多个线程的执行。它允许一个线程发出信号,通知其他等待的线程继续执行。ManualResetEvent 的初始状态可以是有信号(true)或无信号(false),通过调用 Set() 和Reset() 方法来改变其状态

基本用法

ManualResetEvent 的基本用法

  1. 创建 ManualResetEvent 实例    ManualResetEvent  mre = new ManualResetEvent(false);
  2. 线程等到信号:  mre.WaitOne();   //  阻塞当前线程,直到收到信号
  3. 发出信号: mre.Set();    // 发出信号,所有等待的线程将继续执行
  4. 重置信号:mre.Reset();   //将状态重置为无信号,阻塞后续调用WaitOne 的线程 

 控件

  • Proccceed 的功能是发出信号
  • reset 的功能是重置信号   

 展示效果

 实例化 ManualResetEvent

 //因为有4个线程,所以实例化四个
 static ManualResetEvent manual=new ManualResetEvent(true);
 static ManualResetEvent manual2=new ManualResetEvent(true);
 static ManualResetEvent manual3=new ManualResetEvent(true);
 static ManualResetEvent manual4=new ManualResetEvent(true);

 递进增添1

  private void addNum(object obj)
  {
      while (true)
      {
          object[]obb=(object[])obj;
          TextBox tb = (TextBox)obb[0];
          //每次添加1
          tb.Text=(Convert.ToInt16(tb.Text)+1).ToString();
          ManualResetEvent mre = (ManualResetEvent)obb[1];
          //防止线程阻塞
          mre.WaitOne();
          Thread.Sleep(1000);
      }
  }

调用线程池、总功能实现

 private void btn_all_Click(object sender, EventArgs e)
 {
     //创建了两个元素的数组
     //第一个是textBox
     //第二个是manual
     object[] ob1 = new object[2] { textBox1, manual };
     object[] ob2 = new object[2] {textBox2,manual2};
     object[] ob3 = new object[2] {textBox3,manual3};
     object[] ob4 = new object[2] {textBox4,manual4 };
     ThreadPool.QueueUserWorkItem(addNum, ob1);
     ThreadPool.QueueUserWorkItem(addNum, ob2);
     ThreadPool.QueueUserWorkItem(addNum, ob3);
     ThreadPool.QueueUserWorkItem(addNum, ob4);
 }

声明方法

private void operate(ManualResetEvent s)
{
    s.Set();
}
private void Stop(ManualResetEvent v)
{
    v.Reset();
}

发出信号功能

 private void btn_pro1_Click(object sender, EventArgs e)
 {
     operate(manual);
 }
 private void btn_pro2_Click(object sender, EventArgs e)
 {
     operate(manual2);
 }

 private void btn_pro3_Click(object sender, EventArgs e)
 {
     operate(manual3);
 }

 private void btn_pro4_Click(object sender, EventArgs e)
 {
     operate(manual4);
 }

重置信号功能

 private void btn_stop1_Click(object sender, EventArgs e)
 {
     Stop(manual);
 }

 private void btn_stop2_Click(object sender, EventArgs e)
 {
     Stop(manual2);
 }

 private void btn_stop3_Click(object sender, EventArgs e)
 {
     Stop(manual3);
 }

 private void btn_stop4_Click(object sender, EventArgs e)
 {
     Stop(manual4);
 }

线程总代码

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace _15.Using_ThreadPool
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
            CheckForIllegalCrossThreadCalls=false;
        }
        //因为有4个线程,所以实例化四个
        static ManualResetEvent manual=new ManualResetEvent(true);
        static ManualResetEvent manual2=new ManualResetEvent(true);
        static ManualResetEvent manual3=new ManualResetEvent(true);
        static ManualResetEvent manual4=new ManualResetEvent(true);
        private void btn_all_Click(object sender, EventArgs e)
        {
            //创建了两个元素的数组
            //第一个是textBox
            //第二个是manual
            object[] ob1 = new object[2] { textBox1, manual };
            object[] ob2 = new object[2] {textBox2,manual2};
            object[] ob3 = new object[2] {textBox3,manual3};
            object[] ob4 = new object[2] {textBox4,manual4 };
            ThreadPool.QueueUserWorkItem(addNum, ob1);
            ThreadPool.QueueUserWorkItem(addNum, ob2);
            ThreadPool.QueueUserWorkItem(addNum, ob3);
            ThreadPool.QueueUserWorkItem(addNum, ob4);
        }
        private void addNum(object obj)
        {
            while (true)
            {
                object[]obb=(object[])obj;
                TextBox tb = (TextBox)obb[0];
                tb.Text=(Convert.ToInt16(tb.Text)+1).ToString();
                ManualResetEvent mre = (ManualResetEvent)obb[1];
                mre.WaitOne();
                Thread.Sleep(1000);
            }
        }
        private void operate(ManualResetEvent s)
        {
            s.Set();
        }
        private void Stop(ManualResetEvent v)
        {
            v.Reset();
        }
        private void btn_pro1_Click(object sender, EventArgs e)
        {
            operate(manual);
        }
        private void btn_pro2_Click(object sender, EventArgs e)
        {
            operate(manual2);
        }

        private void btn_pro3_Click(object sender, EventArgs e)
        {
            operate(manual3);
        }

        private void btn_pro4_Click(object sender, EventArgs e)
        {
            operate(manual4);
        }

        private void btn_stop1_Click(object sender, EventArgs e)
        {
            Stop(manual);
        }

        private void btn_stop2_Click(object sender, EventArgs e)
        {
            Stop(manual2);
        }

        private void btn_stop3_Click(object sender, EventArgs e)
        {
            Stop(manual3);
        }

        private void btn_stop4_Click(object sender, EventArgs e)
        {
            Stop(manual4);
        }
    }
}