一个简单的利用 HttpClient 异步下载的示例
2018-09-09 16:46 音乐让我说 阅读(640) 评论(0) 编辑 收藏 举报可能你还会喜欢 一个简单的利用 WebClient 异步下载的示例 ,且代码更加新。
1. 定义自己的 HttpClient 类。
using System; using System.Collections.Generic; using System.Globalization; using System.Net; using System.Net.Http; using System.Security.Cryptography; using System.Text; using System.Threading.Tasks; using System.Web; namespace WindowsFormsApplication1.Codes { public class SkyHttpClient { HttpClient client; public string BaseURL { get; } public SkyHttpClient() :this(string.Empty) { } public SkyHttpClient(string baseUrl) { this.BaseURL = baseUrl; InitializeClient(); } public async Task<byte[]> DownloadImage(string url) { return await client.GetByteArrayAsync(url); } void InitializeClient() { client = new HttpClient(); if (!string.IsNullOrEmpty(BaseURL)) { client.BaseAddress = new Uri(BaseURL); client.DefaultRequestHeaders.Add("Referer", BaseURL); client.DefaultRequestHeaders.Add("Origin", BaseURL); } client.DefaultRequestHeaders.Add("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/66.0.3359.139 Safari/537.36"); //client.DefaultRequestHeaders.Add("Accept", "application/json"); } } }
2. 完成核心下载方法。
using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Text; using System.Threading; using System.Threading.Tasks; namespace WindowsFormsApplication1.Codes { public static class TaskDemo101 { public static async Task<bool> RunCore(int id) { SkyHttpClient skyHttpClient = new SkyHttpClient(); string url1 = "http://www.xxx.me/Uploads/image/20130129/2013012920080761761.jpg"; string url2 = "http://www.xxx.me/Uploads/image/20121222/20121222230686278627.jpg"; string url3 = "http://www.xxx.me/Uploads/image/20120606/20120606222018461846.jpg"; string url4 = "http://www.xxx.me/Uploads/image/20121205/20121205224383848384.jpg"; string url5 = "http://www.xxx.me/Uploads/image/20121205/20121205224251845184.jpg"; string resultUrl; int randomNum = new Random().Next(1, 6); switch (randomNum) { case 1: resultUrl = url1; break; case 2: resultUrl = url2; break; case 3: resultUrl = url3; break; case 4: resultUrl = url4; break; case 5: resultUrl = url5; break; default: throw new Exception(""); } var task = skyHttpClient.DownloadImage(resultUrl); return await task.ContinueWith<bool>(t => { var data = t.Result; string targetFolderDestination = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "downloads\\images\\"); try { Directory.CreateDirectory(targetFolderDestination); } catch (Exception) { Console.WriteLine("创建文件夹失败!"); return false; } string targetFileDestination = Path.Combine(targetFolderDestination, string.Format("img_{0}.png", DateTime.Now.ToString("yyyy-MM-dd_HH-mm-ss"))); File.WriteAllBytes(targetFileDestination, data); return true; }); } } }
3. 制作 UI
public partial class Form1 : Form { public Form1() { InitializeComponent(); } private async void button1_Click(object sender, EventArgs e) { try { List<int> ids = new List<int>(100); for (int i = 1; i <= 100; i++) { ids.Add(i); } this.listBoxLog.Items.Insert(0, string.Format("当前时间:{0},准备开始下载...", DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"))); foreach (var id in ids) { bool result = await TaskDemo101.RunCore(id); this.listBoxLog.Items.Insert(0, string.Format("当前时间:{0},编号 {1} 下载 {2}!", DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"), id, result)); } this.listBoxLog.Items.Insert(0, string.Format("当前时间:{0},下载完毕!", DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"))); } catch (Exception ex) { MessageBox.Show(ex.Message, "Download Error!"); } } }
4. 运行截图
5. 疑问
最后,需要注意的是我们的 SkyHttpClient 是每次下载一个图片都会创建一个,那这种每次创建销毁是否会有性能影响呢?在单线程的环境下,我们能否通过外部传入 SkyHttpClient 呢?
比如如下:
6. 最后
参考了文章 https://www.oschina.net/news/77036/httpclient ,发现 HttpClient 建议不要每次都创建新的,而尽量要 static 全局变量缓存,但多线程下也许不安全,所以需要注意最好一个线程使用一个 HttpClient。
还有这篇文章:https://www.cnblogs.com/MingQiu/p/7728443.html
谢谢浏览!
作者:音乐让我说(音乐让我说 - 博客园)
出处:http://music.cnblogs.com/
文章版权归本人所有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。