zoukankan      html  css  js  c++  java
  • 关于异步方法调用

    在我们的程序中,很多时候会有一些耗时较长的运算,我们为了保证用户体验,让用户界面能得到及时的响应。我们一般会采用多线程操作,让耗时操作在
    后台完成,比如我们在上传文件或其他一些需求要在界面显示进度条的例子。在 .NET2.0中为我们供了一个BackGroundWorker类可以完成类似的需求,具体
    使用我们可以参考MSDN。本文要说的我们自己来完成这样一个功能,并封装在通用的基类当中。

    1.我们封装的基类如下:

    public abstract class MyAsyncBaseClass
        {        
            //封装业务方法参数
            private class MyMethodParameters
            {
                public string StringParameter { get; set; }
                public int IntParameter { get; set; }
                public object CallerStateObject { get; set; }
                public System.Windows.Threading.Dispatcher CallingDispatcher { get; set; }
            }
            
            //当线程执行完成后被激发的事件
            public event EventHandler<MyAsyncEventArgs> MyMethodComplete;
            protected void FireMyMethodCompleteEvent(int result, object state)
            {
                if (MyMethodComplete != null)
                {
                    MyMethodComplete(this, new MyAsyncEventArgs(result, state));
                }
            }
    
            //业务逻辑程序
            public abstract int MyMethod(string stringParameter, int intParameter);
            
            // 异步调用的方法
            public void MyMethodAsync(string stringParameer, int intParameter, object state)
            {
                //Instantiate the parameter wrapper.
                MyMethodParameters parameters = new MyMethodParameters()
                {
                    StringParameter = stringParameer,
                    IntParameter = intParameter,
                    CallerStateObject = state,
                   
                    CallingDispatcher = System.Windows.Threading.Dispatcher.CurrentDispatcher
                };            
                //创建线程
                System.Threading.ThreadPool.QueueUserWorkItem(MyMethodThreaded, parameters);
            }
    
            // 线程入口点        
            private void MyMethodThreaded(object p)
            {
                MyMethodParameters parameters = (MyMethodParameters)p;            
                //调用实际的MyMethod方法
                int result = MyMethod(parameters.StringParameter, parameters.IntParameter);
                ///Incorect way to raise event
                ///This would cause a "Cross-thread operation not valid Exception"
                ///FireMyMethodCompleteEvent(result, parameters.CallerStateObject);
                ///
                ///Correct way to raise event
                ///Construct a new delegate with the signature <int, object> and register
                ///it on the caller's event queue.
                parameters.CallingDispatcher.BeginInvoke(
                    new Action<int, object>(FireMyMethodCompleteEvent),
                    result,
                    parameters.CallerStateObject
                );
            }
        }

    2.事件参数如下:

    public class MyAsyncEventArgs : EventArgs
        {
    /// 用户状态对象 public object State { get; protected set; } /// 线程操作完的结果 /// </summary> public int IntResult { get; protected set; } public MyAsyncEventArgs(int result, object state) { State = state; IntResult = result; } }

    3.我们具体要实现的类如下:

    public class MyClass : MyAsyncBaseClass
        {       
            public override int MyMethod(string stringParameter, int intParameter)
            {           
                System.Threading.Thread.Sleep(2000);
                MessageBox.Show("业务逻辑程序执行的地方");
                return 42;
            }
        }

    4.下面我来做下测试,如下:

    image

    public partial class Form1 : Form
        {
           protected MyAsyncBaseClass class1;
    
            public Form1()
            {
                InitializeComponent();
                class1 = new MyClass();            
                class1.MyMethodComplete += MyClass_MyMethodComplete;
            }
            void MyClass_MyMethodComplete(object sender, MyAsyncEventArgs e)
            {         
                object userState = e.State;
                textBox1.Text = String.Format("耗时计算的结果: {0}", e.IntResult);
            }
            private void button1_Click(object sender, EventArgs e)
            {
                class1.MyMethodAsync("A string parameter", 100, this);
            }
        }

  • 相关阅读:
    Python中把数据存入csv文件
    Python中把字典和值取出来
    scrapy输出请求状态码
    scrapy发送post请求获取cookie
    Python3 Unicode转中文
    Quartus13.0破解方法
    元音字母A的发音规则
    位bit——字节Byte???
    曾经的小孩在努力奔跑!
    如何看懂的时序图?
  • 原文地址:https://www.cnblogs.com/carysun/p/AsyncMethodCall.html
Copyright © 2011-2022 走看看