6

最近正在尝试使用 c# 进行异步和等待。这是我的代码

private async void button1_Click( object sender, EventArgs e )
  {
    textBox1.Text = string.Empty;

    var client = new WebClient();

    var sw =  Stopwatch.StartNew();

    var downloadStringTask = client.DownloadStringTaskAsync("http://www.google.com");

    textBox1.Text += "Downloading string async "+sw.ElapsedMilliseconds;
    sw.Restart();

    await downloadStringTask;

    textBox1.Text += Environment.NewLine + "Downloaded "+sw.ElapsedMilliseconds;
    sw.Stop();
}

这是我在 textbox1.text 中得到的输出

Downloading string async 5698
Downloaded 666

这意味着只调用DownloadStringTaskAsync()正在5.6 Seconds执行的实际下载正在执行的地方<1 second。当使用此方法的原因是为了节省线程资源时。

如果这是真的,是否有任何实际情况应该使用 WebClient 类的这种方法?或者我只是在用完全不正确的术语思考?

4

3 回答 3

3

我第一次得到大约 300 毫秒,之后每次都得到 0 毫秒。关于我的期望。当您第一次使用代码时,总会有大量开销。您至少要衡量将 System.Net 代码加载到程序中并进行初始化的成本。WebClient 似乎也有一些开销,例如,当它通过注册表查找 Web 代理时,我看到一个异常被捕获和处理。在异步完成某事之前需要完成的基本工作。

尽管如此,5.7 秒还是很长的时间。你应该看看环境的东西,你机器的其他部分,当你做一些互联网的事情时,你想参与其中。就像那个网络代理一样,它可能被设置为自动配置,这需要时间。或者就像您的反恶意软件或防火墙对您开始使用出站 IP 地址感到兴奋。等等,许多与网络相关的活动部件,它永远不会相同。

于 2013-04-13T12:05:13.817 回答
2

您正在测量设置时间。在我的机器(和 Internet 连接)上,第一个调用产生:

Downloading string async 2636 // Varies wildly, can be up to 15s on some runs.
Downloaded 385

虽然随后的调用始终如一地产生:

Downloading string async 0
Downloaded 289 // With small variations.
于 2013-04-13T12:06:22.427 回答
0

正如其他人所说,您正在衡量一次性设置成本,但作为“多次运行”的替代方法,您可以“预热”特定的 Web 客户端。

例如,在这两行之间,添加一个(同步)下载*调用

var client = new WebClient();

var sw =  Stopwatch.StartNew();

也许是这样的:

var client = new WebClient();

// different site, to help avoid pre-filling any caches involved
client.DownloadData("http://www.microsoft.com/");

var sw =  Stopwatch.StartNew();

那么您的初始测量将不包括初始 Web 客户端设置,即使您的第一次运行也应该有准确的时间(并且应该更好地匹配多次执行相同的调用,假设每次 HTTP 200 结果,而不是从本地缓存或304)

于 2013-04-13T17:10:43.573 回答