什么是AsyncCallback?

RV.*_*RV. 73 c# asynchronous

AsyncCallback的用途是什么?我们为什么要使用它?

Ras*_*dit 141

async方法完成处理时,AsyncCallback将自动调用方法,其中可以执行后处理语句.使用此技术,无需轮询或等待async线程完成.

以下是有关AsyncCallback用法的更多解释:

回调模型:回调模型要求我们指定一个回调方法,并包括我们在回调方法中完成调用所需的任何状态.回调模型可以在以下示例中看到:

static byte[] buffer = new byte[100];

static void TestCallbackAPM()
{
    string filename = System.IO.Path.Combine (System.Environment.CurrentDirectory, "mfc71.pdb");

    FileStream strm = new FileStream(filename,
        FileMode.Open, FileAccess.Read, FileShare.Read, 1024,
        FileOptions.Asynchronous);

    // Make the asynchronous call
    IAsyncResult result = strm.BeginRead(buffer, 0, buffer.Length,
        new AsyncCallback(CompleteRead), strm);
}
Run Code Online (Sandbox Code Playgroud)

在这个模型中,我们创建一个新的AsyncCallback委托,指定一个在操作完成时调用(在另一个线程上)的方法.另外,我们指定了一些我们可能需要的对象作为调用状态.对于此示例,我们将发送流对象,因为我们需要调用EndRead并关闭流.

我们创建的在调用结束时调用的方法如下所示:

static void CompleteRead(IAsyncResult result)
{
    Console.WriteLine("Read Completed");

    FileStream strm = (FileStream) result.AsyncState;

    // Finished, so we can call EndRead and it will return without blocking
    int numBytes = strm.EndRead(result);

    // Don't forget to close the stream
    strm.Close();

    Console.WriteLine("Read {0} Bytes", numBytes);
    Console.WriteLine(BitConverter.ToString(buffer));
}
Run Code Online (Sandbox Code Playgroud)

其他技术是等待直到完成轮询.

Wait-Until-Done模型 wait-until-done模型允许您启动异步调用并执行其他工作.完成其他工作后,您可以尝试结束调用,它将阻塞,直到异步调用完成.

// Make the asynchronous call
strm.Read(buffer, 0, buffer.Length);
IAsyncResult result = strm.BeginRead(buffer, 0, buffer.Length, null, null);

// Do some work here while you wait

// Calling EndRead will block until the Async work is complete
int numBytes = strm.EndRead(result);
Run Code Online (Sandbox Code Playgroud)

或者你可以使用等待句柄.

result.AsyncWaitHandle.WaitOne();
Run Code Online (Sandbox Code Playgroud)

轮询模型轮询方法类似,但代码将轮询IAsyncResult以查看它是否已完成.

// Make the asynchronous call
IAsyncResult result = strm.BeginRead(buffer, 0, buffer.Length, null, null);

// Poll testing to see if complete
while (!result.IsCompleted)
{
    // Do more work here if the call isn't complete
    Thread.Sleep(100);
}
Run Code Online (Sandbox Code Playgroud)

  • `System.IO.Path.Combine`是一种更好的组合路径的方法. (3认同)

bob*_*lex 32

这样想吧.您有一些要并行执行的操作.您可以通过使用异步执行的线程来启用此功能.这是一种解雇机制.

但是有些情况需要一种可以触发并忘记的机制,但在操作完成时需要通知.为此,您将使用异步回调.

操作是异步操作,但在操作完成时会回调您.这样做的好处是你不必等待操作直到它完成.您可以自由执行其他操作,因此您的线程不会被阻止.

一个例子是大文件的后台传输.虽然传输正在进行中,但您并不想阻止用户执行其他操作.转移完成后,该过程将以异步方式回拨您,您可能会弹出一个消息框,其中显示"转移完成"