【问题标题】:Which way is preferred when doing asynchronous WCF calls?进行异步 WCF 调用时首选哪种方式?
【发布时间】:2010-04-10 20:20:08
【问题描述】:

当异步调用 WCF 服务时,似乎有两种方法可以完成。

1.

WcfClient _client = new WcfClient();    
public void One()
{
    _client.BegindoSearch("input", ResultOne, null);
}

private void ResultOne(IAsyncResult ar)
{
    string data = _client.EnddoSearch(ar);
}

2.

public void Two()
{
    WcfClient client = new WcfClient();
    client.doSearchCompleted += TwoCompleted;
    client.doSearchAsync("input");
}

void TwoCompleted(object sender, doSearchCompletedEventArgs e)
{
    string data = e.Result;
}

有了新的Task<T> 类,我们有了第三种简单的方法,将同步操作封装在一个任务中。

3.

public void Three()
{
    WcfClient client = new WcfClient();
    var task = Task<string>.Factory.StartNew(() => client.doSearch("input"));
    string data = task.Result;
}

它们都使您能够在等待结果时执行其他代码,但我认为Task&lt;T&gt; 可以更好地控制您在检索结果之前或之后执行的内容。

使用其中一种有什么优点或缺点?还是一种更可取的方式?

【问题讨论】:

    标签: c# .net wcf asynchronous .net-4.0


    【解决方案1】:

    我会使用最终版本,因为它将在工作线程而不是 I/O 线程上运行操作。如果您在 ASP.NET 中执行此操作,这尤其糟糕,因为需要工作线程来处理请求。更不用说,当您检查其Result 时,您仍在等待任务完成的主线程上阻塞,所以从技术上讲,您正在浪费 两个 工作线程,或者一个工作人员和 UI .

    WCF 客户端的 BeginXYZXyzAsync 方法的工作方式基本相同 - 您应该根据要支持的用例(分别为 APC 或事件驱动)选择适当的版本。例如,BeginXyz 版本(可能违反直觉)更易于在 ASP.NET(或 MVC)异步页面中使用,而XyzAsync 版本更易于在 Windows 窗体中使用。

    【讨论】:

    • Worker 与 IO 线程方面很有趣。我知道线程池每个线程池的数量都是固定的,您可以更改它们。但是框架中的工作线程和IO线程有什么区别。我认为这不仅仅是语义。
    • @Mikael:I/O 线程是为长时间等待而设计的;它们基本上进入睡眠状态并等待 I/O 系统通过中断将它们唤醒。工作线程用于 CPU 繁重的工作,您不希望将它们浪费在阻塞同步 I/O 调用上。
    • 这篇 MSDN 文章中有更多关于工作线程任务的信息 - msdn.microsoft.com/en-us/magazine/ff959203.aspx - 也是关于 .NET 中可用的不同异步方法的良好背景(有点像历史课)跨度>
    【解决方案2】:

    您的第一个示例存在问题。当您调用 EndDoSearch 时,您当然应该创建一个新的 WcfClient 实例。您应该将原始实例保留在字段中或将其作为状态参数传递。

    但总的来说,我更喜欢选项 #1,因为它可以很容易地使用匿名方法来处理结果。

    var client = new WcfClient();
    client.BeginDoSearch("input", ar => {
    
        var result = client.EndDoSearch(ar);
        // blah blah
    
    }, null);
    

    【讨论】:

    • 很好理解;请注意,动态创建 WCF 客户端是很困难的期间 - 通常这些最终是单例/每个会话或由 DI 容器管理。
    • @Josh,我知道我应该使用同一个客户端,现在已经更正了 :)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-12-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-06-27
    相关资源
    最近更新 更多