简体   繁体   English

将回调动作传递给方法

[英]Passing callback Action to a method

It is an asynchronous method that goes and queries the database and sometime returns.它是一种异步方法,可以查询数据库并有时返回。 Currently It is something like this:目前它是这样的:

this.Model.GetStudentKeys(keysList);
this.Foo1();
this.Foo2();

I am not proficient with the syntax but what I need to have is to change the code above in a way that those two Foo methods get called after the Async query is done.我不精通语法,但我需要的是更改上面的代码,以便在 Async 查询完成后调用这两个 Foo 方法。 So I kind of know I need something like this:所以我知道我需要这样的东西:

this.Model.GetStudentKeys(keysList, callBack);

Action<object> callback {
    this.Foo1();
    this.Foo2();
}

But like I said I am not familiar with the syntax.但就像我说的,我不熟悉语法。 Can you please help me with it?你能帮我吗?

You can use callbacks, but they are being superseded by C#'s async/await syntax .您可以使用回调,但它们正在被 C# 的async/await 语法取代 Before I explain said syntax however, I'll show you how you can achieve the same with Action s:但是,在解释上述语法之前,我将向您展示如何使用Action实现相同的效果:

/*Action is a reference type, so its assignment is no different. Its value is a lambda
  expression (http://msdn.microsoft.com/en-us/library/bb397687.aspx),
  which you can think of as an anonymous method.*/
private Action<object> callback = o =>
                             {
                                 object result = o;

                                 this.Foo1();
                                 this.Foo2();
                             };

/*It's good practice in C# to append 'Async' to the name of an asynchronous method
  in case a synchronous version is implemented later.*/
this.Model.GetStudentKeysAsync(keysList, callback);

With this approach, your GetStudentsAsync method must invoke the callback, like so:使用这种方法,您的GetStudentsAsync方法必须调用回调,如下所示:

public void GetStudentsAsync(List<string> keys, Action<object> callback)
{
    var returnValue = null;
    //do some stuff...
    callback(returnValue);
} 

You can also pass the lambda expression directly as a parameter:您还可以直接将 lambda 表达式作为参数传递:

this.Model.GetStudentKeysAsync(keysList, o =>
                             {
                                 this.Foo1();
                                 this.Foo2();
                             });

With .NET 4.5 (and .NET 4.0 using the Microsoft Async package ) however, you can use the async and await keywords provided by C# 5:但是,对于 .NET 4.5(以及使用Microsoft Async 包的.NET 4.0),您可以使用 C# 5 提供的asyncawait关键字:

//notice the 'async' keyword and generic 'Task(T)' return type
public async Task<IEnumerable<StudentModel>> GetStudentsAsync(IEnumerable<int> keyList)
{
    /*to invoke async methods, precede its invocation with
      the 'await' keyword. This allows program flow to return
      the line on which the GetStudentsAsync method was called.
      The flow will return to GetStudentsAsync once the database
      operation is complete.*/

    IEnumerable<StudentModel> students = await FakeDatabaseService.ExecuteSomethingAsync();

    return students;
}

Simply invoke the above method as follows:简单的调用上面的方法如下:

IEnumerable<StudentModel> students = await this.Model.GetStudentsAsync(keyList);

Assuming the GetStudentKeys method returns a Task object (due to it being async), you could use the (new in C# 5.0) construct async and await ,假设GetStudentKeys方法返回一个Task对象(由于它是异步的),您可以使用(C# 5.0 中的新功能)构造asyncawait

public async void MethodName()
{
    await this.Model.GetStudentKeysAsync(keysList);    // <-- Async operation
    this.Foo1();
    this.Foo2();
}

Once the async operation completes, the code will then continue after the await keyword.异步操作完成后,代码将在await关键字之后继续。

You can define your function like that你可以这样定义你的函数

    void GetStudentKeys(keysList, Func<bool> callback)
    {
        Thread th = new Thread(delegate(){
            //do some work in separate thread and inside that thread call
            if(callback != null)
                callback();
        });
        th.Start();
    }

and change the function call to并将函数调用更改为

    this.Model.GetStudentKeys(keysList, () => {
        this.Foo1();
        this.Foo2();
        return true;
    });

Something like that.类似的东西。

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

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