【问题标题】:How to Optimize C# Async Calls如何优化 C# 异步调用
【发布时间】:2014-04-11 05:01:24
【问题描述】:

我是 C# 的异步世界的新手,诚然对这个主题没有太多了解。我只需要在我们的一项服务中实现它,我对它的工作原理有点困惑。我想尽可能快地发布到 API。我对获得响应并对其进行处理需要多长时间不太感兴趣。这是我正在做的一个例子。

        foreach (var item in list)
        {
            callPostFunction(item.data);
            log("Posted");
        }

    public async void callPostFunction(PostData data)
    {
        var apiResult = await postToAPI(data);
        updateDB(apiResult);
    }

    public static async Task<string> postToAPI(PostData dataToSend)
    {
        var url = "Example.com";

        HttpWebRequest httpWReq = (HttpWebRequest)WebRequest.Create(url);
        ASCIIEncoding encoding = new ASCIIEncoding();
        string postData = dataToSend;
        byte[] dataBytes = encoding.GetBytes(postData);

        httpWReq.Method = "POST";
        httpWReq.ContentType = "application/x-www-form-urlencoded";
        httpWReq.ContentLength = dataBytes.Length;
        httpWReq.Accept = "application/json, application/xml, text/json, text/x-json, text/javascript, text/xml";

        using (var stream = await httpWReq.GetRequestStreamAsync())
        {
            await stream.WriteAsync(dataBytes, 0, dataBytes.Length);
        }

        HttpWebResponse response = (HttpWebResponse)httpWReq.GetResponse();

        return new StreamReader(response.GetResponseStream()).ReadToEnd();
    }

如果我将 1000 个项目放入列表中,“已发布”会立即记录 1000 次。太好了,流程完成了,可以继续做其他事情了。问题是 callPostFunction 在后台某处调用 postToAPI 并发布到 API,它可以工作,但需要很长时间。它需要与实现异步之前一样长(尽管没有那么长)。我觉得我错过了什么。

我必须尽快访问 API。理想情况下,我想在 callPostFunction 几乎立即被调用时经常点击它。我该怎么做呢?

【问题讨论】:

  • 拥有async void 方法,除非它是您堆栈最顶端的方法,否则通常是一个有缺陷的设计。
  • 但是,在这个例子中,我将如何让我的进程(foreach)尽可能快地运行记录。如果 callPostFunction 返回了一些东西,对它的调用不是必须等待它吗?
  • 不,它不必等待它,或者至少不用马上。通常,您希望看到的内容类似于await Task.WhenAll(tasksForEachIndividualRequest);。然后你会做任何总结,记录,或者在那之后的任何其他事情。如果您真的不想这样做,您仍然可以调用该方法并忽略该任务,但是通过让该方法返回一个任务,这意味着如果该方法的其他调用者在某处否则确实await它,它可以。通过将其设为void,您是在说没有人,在任何时候,都需要await

标签: c# api rest asynchronous async-await


【解决方案1】:

ServicePointManager.DefaultConnectionLimit 设置为int.MaxValue

另外,正如@Servy 指出的那样,避免使用async void

【讨论】:

    【解决方案2】:

    你并没有错过什么。发布一堆数据需要时间。网络连接很慢。他们的带宽有限。异步执行这项工作并不是提高速度的灵丹妙药。它的目的也不是优化速度。

    【讨论】:

    • +1,但我认为您的答案需要(希望)包括您在上面关于堆栈顶部的评论以及这对于避免饱和至关重要的事实。 :)
    • @Moo-Juice 这与提出的实际问题无关。这是一个有趣的切线,但仍然偏离手头的问题,这就是为什么它出现在评论中,而不是答案中。
    • 公平点,切线有些皱眉头:)但是很好的答案。
    猜你喜欢
    • 2020-07-15
    • 1970-01-01
    • 2012-04-05
    • 2017-04-01
    • 1970-01-01
    • 2018-03-06
    • 2021-03-21
    • 2018-07-16
    • 1970-01-01
    相关资源
    最近更新 更多