C#中用SemaphoreSlim信号量来代替线程Thread实现多并发操作

之前在写C#多线程,多并发操作的时候,一直都用Thread来实现的,但是发现有一个问题,就是用Thread的话,如果暂时没有要处理的数据,会多条线程一直在空转。最近学了SemaphoreSlim信号量后,发现这个玩意用起来比较舒服。只需要确定一下最大的并发数,就可以自动调控了。也不会出现空转的情况。


这个是效果图。演示从1到1万循环,并且开n个并发。下面是测试代码。大家可以自行参考一下。

namespace 信号量并发测试
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        // 最大并发
        const int MaxConcurrency = 500;
        SemaphoreSlim semaphore = new SemaphoreSlim(MaxConcurrency);
        int index = 0;


        private async void button1_Click(object sender, EventArgs e)
        {
            index = 0;
            listBox1.Items.Clear();
            button1.Enabled = false;

            try
            {
                await RunTask();
            }
            catch (Exception ex)
            {
                MessageBox.Show($"测试出错:{ex.Message}", "错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            finally
            {
                button1.Enabled = true;
            }
        }

        private async Task RunTask()
        {
            var tasks = new List<Task>();
            while (true)
            {
                int num = Interlocked.Increment(ref index);

                if (num > 10000)
                {
                    break;
                }

                await semaphore.WaitAsync();

                this.BeginInvoke(() =>
                {
                    label1.Text = $"并发:{MaxConcurrency - semaphore.CurrentCount}/{MaxConcurrency}";
                });

                Task t = Task.Run(async () =>
                  {
                      try
                      {
                          this.BeginInvoke(() =>
                          {
                              listBox1.Items.Insert(0, $"数字:{num}  时间:{DateTime.Now:HH:mm:ss.fff}");
                          });

                          await Task.Delay(300); // 模拟异步耗时
                      }
                      finally
                      {
                          semaphore.Release();

                          this.BeginInvoke(() =>
                          {
                              label1.Text = $"并发:{MaxConcurrency - semaphore.CurrentCount}/{MaxConcurrency}";
                          });
                      }
                  });

                tasks.Add(t);
            }

            await Task.WhenAll(tasks);
        }

        private void button2_Click(object sender, EventArgs e)
        {
            button2.Enabled = false;
            var threads = new List<Thread>();
            index = 0;

            for (int i = 0; i < MaxConcurrency; i++)
            {                
                Thread t = new Thread(() =>
                {
                    while (true)
                    {
                        int num = Interlocked.Increment(ref index);
                        if (num > 10000)
                        {
                            break;
                        }

                        this.BeginInvoke((Delegate)(() =>
                        {
                            listBox1.Items.Insert(0, $"数字:{num}  时间:{DateTime.Now:HH:mm:ss.fff}");
                        }));
                        Thread.Sleep(300); // 模拟耗时
                    }                    
                });
                t.Start();

                threads.Add(t);
            }

            foreach (var t in threads)
            {
                t.Join();
            }

            button2.Enabled = true;
        }
    }
}

  1. 本网站所收集的部分资料来源于互联网,本站不对其真实性负责,也不构成任何其他建议。如果您发现有侵犯您权益的内容,请与我们取得联系,我们会及时修改或删除。
  2. 传递知识、传递力量,欢迎各位网友对本站的文章进行转载和分享。
  3. 本站QQ群交流群:904314688  群号:904314688
发表评论
 
评论列表(目前共有 条评论)
暂时还没有评论哦~

文章搜索

商家广告


版权所有:秋风雅居 (www.198933.com) ©2026 All Rights Reserved.

粤ICP备20031662号