简体   繁体   English

WaitHandle同步的价格是多少?

[英]How expensive is the WaitHandle synchronization?

I have heard that WaitHandle derived synchronization primitives are expensive, but couldn't find further details. 我听说, WaitHandle派生的同步原语很昂贵,但是找不到更多详细信息。 Is there any performance comparison to other equivalent or similar primitives available? 是否有与其他等效或相似原语的性能比较?

For one particular case, where AutoResetEvent and Monitor can be interchanged, the performance of the monitor is at least 1.5 times better (2 times typically). 在一种特殊情况下,可以互换AutoResetEventMonitor ,则Monitor的性能至少要好1.5倍(通常是2倍)。 This statement is based on the following raw producer/consumer test (Release build) and is valid in the case there is no error in the test logic :o) Anyway, might be usefull for someone... 该语句基于以下原始生产者/消费者测试(发布版本),并且在测试逻辑没有错误的情况下有效:o)无论如何,对于某人可能有用...

Now, I'm trying to be the one who races the horses ;) 现在,我正在努力成为参加比赛的人 ;)

Code: 码:

using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Threading;
using Timer = System.Timers.Timer;

namespace ThreadSync2
{
    static class Measurement
    {
        private static readonly Random rng = new Random();

        private static long Evaluate(string methodName, Action signal, Action wait)
        {
            var isProducing = false;
            var isConsuming = false;
            var mtxData     = new object(); 
            var data        = new Queue<Tuple<long,int>>();
            var produced    = 0L;
            var consumed    = 0L;
            var watch       = new Stopwatch();

            var producer = new Thread(() => 
            {
                Debug.WriteLine("Production : started.");

                while (isProducing)
                {
                    var item = rng.Next(0, 100);

                    lock (mtxData)
                        data.Enqueue(new Tuple<long, int>(produced, item));

                    signal();
                    Debug.WriteLine($"{watch.Elapsed.Seconds,3:d}.{watch.Elapsed.Milliseconds:d3} Producer: {produced,6:d} [{item,3:d}]");

                    ++produced;
                }

                Debug.WriteLine("Production : finished.");
            }){Name = "Producer"};

            var consumer = new Thread(() => 
            {
                Debug.WriteLine("Consumption: started.");

                while (   (isConsuming)
                       || (data.Count > 0))
                {
                    while (data.Count > 0)
                    {
                        Tuple<long, int> record;

                        lock (mtxData)
                            record = data.Dequeue();

                        Debug.WriteLine($"{watch.Elapsed.Seconds,3:d}.{watch.Elapsed.Milliseconds:d3} Consumer: {record.Item1,6:d} [{record.Item2,3:d}]");
                        ++consumed;
                    }

                    wait();
                }

                Debug.WriteLine("Consumption: finished.");
            }){Name = "Consumer"};

            var timer = new Timer(5000){AutoReset = false};
            timer.Elapsed += (s, e) => {isProducing = false;};

            Console.WriteLine($"Evaluating \"{methodName}\"...");
            watch.Start();
            timer.Enabled = true;
            isConsuming = true;
            isProducing = true;
            consumer.Start();
            producer.Start();            
            producer.Join();
            isConsuming = false;
            consumer.Join();
            watch.Stop();

            Console.WriteLine($"Produced items: {produced:### ### ##0}{((produced != consumed) ? $", Consumed items: {consumed:### ### ##0}" : "")}");
            Console.WriteLine();

            return produced;
        }

        public static void Evaluate()
        {
            const string strMonitorLock = "Monitor locking";
            const string strWaitHandle  = "AutoResetEvent";
            const int    waitTimeout    = 500;

            var semMonitorLock = new object();
            var semWaitHandle  = new AutoResetEvent(false);

            var cntMonitorLock = Evaluate
            (
                strMonitorLock,
                () => {lock (semMonitorLock) Monitor.Pulse(semMonitorLock);},
                () => {lock (semMonitorLock) Monitor.Wait (semMonitorLock, waitTimeout);}
            );

            var cntWaitHandle = Evaluate
            (
                strWaitHandle,
                () => semWaitHandle.Set(),
                () => semWaitHandle.WaitOne(waitTimeout)
            );

            Console.WriteLine($"{strMonitorLock} / {strWaitHandle} = {((double)cntMonitorLock / cntWaitHandle):0.000}");
            Console.WriteLine();
        }
    }

    class Program
    {
        static Program()
        {
            Debug.Listeners.Add(new TextWriterTraceListener(Console.Out));
        }

        static void Main(string[] args)
        {
            Measurement.Evaluate();
        }
    }
}

Console output for repeated executions: 重复执行的控制台输出:

Evaluating "Monitor locking"...
    Produced items: 15 710 306

    Evaluating "AutoResetEvent"...
    Produced items: 5 998 742

    Monitor locking / AutoResetEvent = 2,619

    Evaluating "Monitor locking"...
    Produced items: 11 697 953

    Evaluating "AutoResetEvent"...
    Produced items: 7 119 778

    Monitor locking / AutoResetEvent = 1,643

    Evaluating "Monitor locking"...
    Produced items: 11 662 575

    Evaluating "AutoResetEvent"...
    Produced items: 6 437 772

    Monitor locking / AutoResetEvent = 1,812

    Evaluating "Monitor locking"...
    Produced items: 12 981 254

    Evaluating "AutoResetEvent"...
    Produced items: 5 934 954

    Monitor locking / AutoResetEvent = 2,187

    Evaluating "Monitor locking"...
    Produced items: 14 661 293

    Evaluating "AutoResetEvent"...
    Produced items: 6 370 518

    Monitor locking / AutoResetEvent = 2,301

    Evaluating "Monitor locking"...
    Produced items: 15 050 786

    Evaluating "AutoResetEvent"...
    Produced items: 5 912 671

    Monitor locking / AutoResetEvent = 2,546

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM