• C# 多线程编程 使用委托创建线程


    进程和线程

    进程:进程包含资源,例如windows句柄,文件系统句柄或者其他核心对象,每个进程都分配了虚拟内存。一个进程至少包含一个线程。操作系统会调度线程。

    进程管理的资源包括虚拟内存和windows句柄。

    线程: 都有自己的堆栈,但程序代码的内存和堆由一个进程内所有的线程共享。

    在.NET中,托管的线程由Thread类定义。托管的线程不一定映射为一个操作系统线程。

    使用委托创建线程的三种方法

    1. Pooling 投票方式

    2. WaitHandle 等待句柄

    3. Asynchronous Call 异步回调

    // 异步委托示例
    // Herbert
    // 个人学习使用
    
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Threading;
    using System.Diagnostics;
    
    namespace AsyDelegate
    {
        class Program
        {
            public delegate int TakesAWhileDelegate(int data, int ms);
    
            static int TakesAWhile(int data, int ms)
            {
                Console.WriteLine("TakesAWhile started");
                Thread.Sleep(ms);
                Console.WriteLine("TalesAWhile completed");
                return ++data; 
            }
    
            public static void Method1()
            {
                // 第一种投票方式
                // synchronouse method call
                // TakesAWhile(1, 3000)
                // Asynchronous by using a delegate
                // IAsyncResult 可以获得委托信息,并验证委托是否完成了任务
    
                TakesAWhileDelegate dl = TakesAWhile;
    
                IAsyncResult ar = dl.BeginInvoke(1, 3000, null, null);
                while (!ar.IsCompleted)
                {
                    // do something else in the main thread
                    Console.Write(".");
                    Thread.Sleep(50);
                }
    
                int result = dl.EndInvoke(ar);
                Console.WriteLine("result: {0}", result);          
            }
    
            public static void Method2()
            {
                // 第二种等待句柄方式            
                // synchronouse method call
                // TakesAWhile(1, 3000)
                // Asynchronous by using a delegate
                // WaitOne()将一个超时时间作为可选的第一个参数,定义要等待的最大时间
    
                TakesAWhileDelegate dl = TakesAWhile;
    
                IAsyncResult ar = dl.BeginInvoke(1, 3000, null, null);
                while (true)
                {
                    // do something else in the main thread
                    Console.Write(".");
                    if (ar.AsyncWaitHandle.WaitOne(50, false))
                    {
                        Console.WriteLine("Can get the result now");
                        break;
                    }
                }
    
                int result = dl.EndInvoke(ar);
                Console.WriteLine("result: {0}", result);           
            }
    
            public static void TakesAWhileCompleted(IAsyncResult ar)
            {
                // 第三种方式异步回调
    
                if (ar == null)
                    throw new ArgumentNullException("ar");
                TakesAWhileDelegate d1 = ar.AsyncState as TakesAWhileDelegate;
                Trace.Assert(d1 != null, "Invalid object type");
    
                int result = d1.EndInvoke(ar);
                Console.WriteLine("result : {0}", result); 
            }
    
            static void Main(string[] args)
            {
                Stopwatch sw1 = new Stopwatch();
                Console.WriteLine("Method 1 Pooling started:");
                sw1.Start();
                Program.Method1();
                sw1.Stop();
                Console.WriteLine(sw1.ElapsedMilliseconds.ToString());
    
                Stopwatch sw2 = new Stopwatch();
                Console.WriteLine("Method 2 Wait Handler started:");
                sw2.Start();
                Program.Method2();
                sw2.Stop();
                Console.WriteLine(sw2.ElapsedMilliseconds.ToString());
    
                Stopwatch sw3 = new Stopwatch();
                Console.WriteLine("Method 3 Asynchronize CallBack started:");
                sw3.Start();
                TakesAWhileDelegate d1 = TakesAWhile;
                
                /*
                d1.BeginInvoke(1, 3000, ar => 
                {
                    int result = d1.EndInvoke(ar);
                    Console.WriteLine("result: {0}", result);
                }), null;
                 */ 
                d1.BeginInvoke(1, 3000, TakesAWhileCompleted, d1);
    
                for (int i = 0; i < 100; i++)
                {
                    Console.Write(".");
                    Thread.Sleep(50);
                }
                Console.WriteLine(sw3.ElapsedMilliseconds.ToString());
    
                Console.ReadKey();            
            }
        }
    }
    

    通过运行时间进行比较, 投票方式和异步回调比较好用,似乎投票方式效率会低些,而异步回调效率最高。

  • 相关阅读:
    Ubuntu安装teamviewer(附带解决dpkg占用的代码)
    使用print时出错 SyntaxError: Missing parentheses in call to 'print' Did you mean print("Usage....
    非root用户(普通用户)安装CMake
    Permanently added the RSA host key for IP address '13.229.188.59' Permission denied (publickey)fatal
    django6-admin
    django6-信号
    django6-缓存
    django6 -中间件
    天津去哪玩
    django--->form表单
  • 原文地址:https://www.cnblogs.com/herbert/p/1765134.html
Copyright © 2020-2023  润新知