【代码】C#中Invoke与BeginInvoke的用法

2022-02-22 17:01:59  阅读 707 次 评论 0 条

Invoke与Begining的区别:

Invoke会阻塞当前线程,知道invoke结束才会去执行下面的代码。

而BeginInvoke则可以异步调用,也就是方法封送完后马上返回,不必等待执行结束,调用的线程不会被阻塞。

调用者可以使用EndInvoke或者其它类似WaitHandle机制等待异步操作的完成。

先说下Invoke

class Program
    {
        
        static void Main(string[] args)
        {
            MyProgram mp = new MyProgram();
            mp.removeUser("12a");
        }
    }


    public class MyProgram
    {
        public delegate string myDelegate(string logTxt);
        public void removeUser(string userid)
        {
            ///方法体
            
            myDelegate deleg = new myDelegate(Utils.postLog);
            
            string gres=deleg.Invoke("这个是方法的参数");//这个是方法的参数
            int a = 1;
                        int b = 2;
                        int c = 3;
                        Console.WriteLine(a+b+c);
            Console.WriteLine(gres);
            Console.ReadKey();
        }
    }

    public class Utils
    {
        public static string postLog(string logTxt)
        {
            string res = string.Empty;
            ///方法体
            Thread.Sleep(5000);//线程休息5秒,模拟request请求延迟
            res = "OK";
            return res;
        }
    }


这里Invoke 必须等委托函数调用完成之后,才会执行后面操作,那么当我们的委托函数执行的是一个非常耗时的操作

这样线程就会被阻塞,造成用户操作卡顿的情况,所以,为了解决invoke同步的问题,还有一种就是beginInvoke

BeginInvoke方法触发你的异步方法,它和你想要执行的异步方法有相同的参数。另外还有两个可选参数,第一个是AsyncCallback委托是异步完成的回调方法。第二个是用户自定义对象,该对象将传递到回调方法中。BeginInvoke立即返回并且不等待完成异步的调用(继续执行该下面的代码,不需要等待)。BeginInvoke返回IAsyncResult接口,可用于检测异步调用的过程。

通过EndInvoke方法检测异步调用的结果。如果异步调用尚未完成,EndInvoke将阻塞调用线程,直到它完成。EndInvoke参数包括out和ref参数。

不管怎么么样,调用了beginInvoke ,就必须调用endInvoke 结束异步,

那我们怎么才能知道什么时候异步结束呢,常见四种方法:

1、做一些其他操作,然后调用EndInvoke方法阻塞线程直到该方法完成。

2、使用IAsyncResult.AsyncWaitHandle属性,使用它的WaitOne方法阻塞线程直到收到WaitHandle信号,然后调用EndInvoke。

3、检查BeginInvoke返回值IAsyncResult的状态来决定方法是否完成,然后调用EndInvoke方法。

4、通过在BeginInvoke方法中传递该委托,在回调方法中调用该委托的EndInvoke方法。


下面是BeginInvoke

class Program
    {
        
        static void Main(string[] args)
        {
            MyProgram mp = new MyProgram();
            mp.removeUser("12a");
        }
    }


    public class MyProgram
    {
        public delegate string myDelegate(string logTxt);
        public void removeUser(string userid)
        {
            ///方法体
            
            myDelegate deleg = new myDelegate(Utils.postLog);

            IAsyncResult res = deleg.BeginInvoke("用户1删除成功", null, null); //参数各自是 委托的参数(可能有多个),执行后的回调(不需要可以null),异步状态
            
            int a = 1;
            int b = 2;
            int c = 3;
            Console.WriteLine(a+b+c);
            string gres = deleg.EndInvoke(res);
            Console.WriteLine(gres);
            Console.ReadKey();

        }
    }

    public class Utils
    {
        public static string postLog(string logTxt)
        {
            string res = string.Empty;
            ///方法体
            Thread.Sleep(5000);//线程休息5秒,模拟request请求延迟
            res = "OK";
            return res;
        }
    }



微信扫码查看本文
本文地址:https://www.yangguangdream.com/?id=2195
版权声明:本文为原创文章,版权归 编辑君 所有,欢迎分享本文,转载请保留出处!

发表评论


表情

还没有留言,还不快点抢沙发?