C#中HttpWebRequest、WebClient、HttpClient的使用详解
HttpWebRequest:
命名空间:System.Net,这是.NET创建者最初开发用于使用HTTP请求的标准类。使用HttpWebRequest可以让开发者控制请求/响应流程的各个方面,如timeouts,cookies,headers,protocols。另一个好处是HttpWebRequest类不会阻塞UI线程。例如,当您从响应很慢的API服务器下载大文件时,您的应用程序的UI不会停止响应。HttpWebRequest通常和WebResponse一起使用,一个发送请求,一个获取数据。HttpWebRquest更为底层一些,能够对整个访问过程有个直观的认识,但同时也更加复杂一些。
//POST方法 publicstaticstringHttpPost(stringUrl,stringpostDataStr) { HttpWebRequestrequest=(HttpWebRequest)WebRequest.Create(Url); request.Method="POST"; request.ContentType="application/x-www-form-urlencoded"; Encodingencoding=Encoding.UTF8; byte[]postData=encoding.GetBytes(postDataStr); request.ContentLength=postData.Length; StreammyRequestStream=request.GetRequestStream(); myRequestStream.Write(postData,0,postData.Length); myRequestStream.Close(); HttpWebResponseresponse=(HttpWebResponse)request.GetResponse(); StreammyResponseStream=response.GetResponseStream(); StreamReadermyStreamReader=newStreamReader(myResponseStream,encoding); stringretString=myStreamReader.ReadToEnd(); myStreamReader.Close(); myResponseStream.Close(); returnretString; } //GET方法 publicstaticstringHttpGet(stringUrl,stringpostDataStr) { HttpWebRequestrequest=(HttpWebRequest)WebRequest.Create(Url+(postDataStr==""?"":"?")+postDataStr); request.Method="GET"; request.ContentType="text/html;charset=UTF-8"; HttpWebResponseresponse=(HttpWebResponse)request.GetResponse(); StreammyResponseStream=response.GetResponseStream(); StreamReadermyStreamReader=newStreamReader(myResponseStream,Encoding.GetEncoding("utf-8")); stringretString=myStreamReader.ReadToEnd(); myStreamReader.Close(); myResponseStream.Close(); returnretString; }
WebClient:
命名空间System.Net,WebClient是一种更高级别的抽象,是HttpWebRequest为了简化最常见任务而创建的,使用过程中你会发现他缺少基本的header,timeoust的设置,不过这些可以通过继承httpwebrequest来实现。相对来说,WebClient比WebRequest更加简单,它相当于封装了request和response方法,不过需要说明的是,Webclient和WebRequest继承的是不同类,两者在继承上没有任何关系。使用WebClient可能比HttpWebRequest直接使用更慢(大约几毫秒),但却更为简单,减少了很多细节,代码量也比较少。
publicclassWebClientHelper { publicstaticstringDownloadString(stringurl) { WebClientwc=newWebClient(); //wc.BaseAddress=url;//设置根目录 wc.Encoding=Encoding.UTF8;//设置按照何种编码访问,如果不加此行,获取到的字符串中文将是乱码 stringstr=wc.DownloadString(url); returnstr; } publicstaticstringDownloadStreamString(stringurl) { WebClientwc=newWebClient(); wc.Headers.Add("User-Agent","Mozilla/5.0(WindowsNT10.0;Win64;x64)AppleWebKit/537.36(KHTML,likeGecko)Chrome/76.0.3809.132Safari/537.36"); StreamobjStream=wc.OpenRead(url); StreamReader_read=newStreamReader(objStream,Encoding.UTF8);//新建一个读取流,用指定的编码读取,此处是utf-8 stringstr=_read.ReadToEnd(); objStream.Close(); _read.Close(); returnstr; } publicstaticvoidDownloadFile(stringurl,stringfilename) { WebClientwc=newWebClient(); wc.DownloadFile(url,filename);//下载文件 } publicstaticvoidDownloadData(stringurl,stringfilename) { WebClientwc=newWebClient(); byte[]bytes=wc.DownloadData(url);//下载到字节数组 FileStreamfs=newFileStream(filename,FileMode.Create); fs.Write(bytes,0,bytes.Length); fs.Flush(); fs.Close(); } publicstaticvoidDownloadFileAsync(stringurl,stringfilename) { WebClientwc=newWebClient(); wc.DownloadFileCompleted+=DownCompletedEventHandler; wc.DownloadFileAsync(newUri(url),filename); Console.WriteLine("下载中。。。"); } privatestaticvoidDownCompletedEventHandler(objectsender,AsyncCompletedEventArgse) { Console.WriteLine(sender.ToString());//触发事件的对象 Console.WriteLine(e.UserState); Console.WriteLine(e.Cancelled); Console.WriteLine("异步下载完成!"); } publicstaticvoidDownloadFileAsync2(stringurl,stringfilename) { WebClientwc=newWebClient(); wc.DownloadFileCompleted+=(sender,e)=> { Console.WriteLine("下载完成!"); Console.WriteLine(sender.ToString()); Console.WriteLine(e.UserState); Console.WriteLine(e.Cancelled); }; wc.DownloadFileAsync(newUri(url),filename); Console.WriteLine("下载中。。。"); } }
HttpClient:
HttpClient是.NET4.5引入的一个HTTP客户端库,其命名空间为System.Net.Http,.NET4.5之前我们可能使用WebClient和HttpWebRequest来达到相同目的。HttpClient利用了最新的面向任务模式,使得处理异步请求非常容易。它适合用于多次请求操作,一般设置好默认头部后,可以进行重复多次的请求,基本上用一个实例可以提交任何的HTTP请求。HttpClient有预热机制,第一次进行访问时比较慢,所以不应该用到HttpClient就new一个出来,应该使用单例或其他方式获取HttpClient的实例
单例模式:
单例模式(SingletonPattern)这种类型的设计模式属于创建型模式,它提供了一种创建对象的最佳方式。
这种模式涉及到一个单一的类,该类负责创建自己的对象,同时确保只有单个对象被创建。这个类提供了一种访问其唯一的对象的方式,可以直接访问,不需要实例化该类的对象。
单例创建步骤:1、定义静态私有对象;2、定义私有构造函数;3、提供公共获取对象方法;
单例模式一般分为两种实现模式:懒汉模式、饿汉模式(以下为Java代码实现)
懒汉模式:默认不会实例化,什么时候用什么时候new
publicclassSingleton{ privatestaticSingletoninstance=null; privateSingleton(){} publicstaticSingletongetInstance(){ if(instance==null){ instance=newSingleton(); } returninstance; } }
这种方式是最基本的实现方式,这种实现最大的问题就是不支持多线程。因为没有加锁synchronized,所以严格意义上它并不算单例模式。
这种方式lazyloading很明显,不要求线程安全,在多线程不能正常工作。
饿汉模式:类初始化时,会立即加载该对象,线程天生安全,调用效率高
publicclassSingleton{ privatestaticSingletoninstance=newSingleton(); privateSingleton(){} publicstaticSingletongetInstance(){ returninstance; } }
双检锁/双重校验锁(DCL,即double-checkedlocking):这种方式采用双锁机制,安全且在多线程情况下能保持高性能
publicclassSingleton{ privatevolatilestaticSingletonsingleton; privateSingleton(){} publicstaticSingletongetSingleton(){ if(singleton==null){ synchronized(Singleton.class){ if(singleton==null){ singleton=newSingleton(); } } } returnsingleton; } }
HttpClient:
publicclassHttpClientHelper { privatestaticreadonlyobjectLockObj=newobject(); privatestaticHttpClientclient=null; publicHttpClientHelper(){ GetInstance(); } publicstaticHttpClientGetInstance() { if(client==null) { lock(LockObj) { if(client==null) { client=newHttpClient(); } } } returnclient; } publicasyncTaskPostAsync(stringurl,stringstrJson)//post异步请求方法 { try { HttpContentcontent=newStringContent(strJson); content.Headers.ContentType=newSystem.Net.Http.Headers.MediaTypeHeaderValue("application/json"); //由HttpClient发出异步Post请求 HttpResponseMessageres=awaitclient.PostAsync(url,content); if(res.StatusCode==System.Net.HttpStatusCode.OK) { stringstr=res.Content.ReadAsStringAsync().Result; returnstr; } else returnnull; } catch(Exceptionex) { returnnull; } } publicstringPost(stringurl,stringstrJson)//post同步请求方法 { try { HttpContentcontent=newStringContent(strJson); content.Headers.ContentType=newSystem.Net.Http.Headers.MediaTypeHeaderValue("application/json"); //client.DefaultRequestHeaders.Connection.Add("keep-alive"); //由HttpClient发出Post请求 Task res=client.PostAsync(url,content); if(res.Result.StatusCode==System.Net.HttpStatusCode.OK) { stringstr=res.Result.Content.ReadAsStringAsync().Result; returnstr; } else returnnull; } catch(Exceptionex) { returnnull; } } publicstringGet(stringurl) { try { varresponseString=client.GetStringAsync(url); returnresponseString.Result; } catch(Exceptionex) { returnnull; } } }
HttpClient有预热机制,第一次请求比较慢;可以通过初始化前发送一次head请求解决:
_httpClient=newHttpClient(){BaseAddress=newUri(BASE_ADDRESS)}; //帮HttpClient热身 _httpClient.SendAsync(newHttpRequestMessage{ Method=newHttpMethod("HEAD"), RequestUri=newUri(BASE_ADDRESS+"/")}) .Result.EnsureSuccessStatusCode();
三者区别列表:
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持毛票票。
声明:本文内容来源于网络,版权归原作者所有,内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎发送邮件至:czq8825#qq.com(发邮件时,请将#更换为@)进行举报,并提供相关证据,一经查实,本站将立刻删除涉嫌侵权内容。