日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > asp.net >内容正文

asp.net

.NET Socket服务编程之-高效连接接入编

發布時間:2025/3/19 asp.net 18 豆豆
生活随笔 收集整理的這篇文章主要介紹了 .NET Socket服务编程之-高效连接接入编 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

? ? ? ? 在.NET上編寫網絡服務深入都有2,3年了,而這些時間時如何在.NET里實現網絡服務積累了一些經驗.在接下來的時間里會把這方面的經驗通過博客的方式分享出來.而這一章主要是講解在如果提高服務連接接入的效率,從而讓服務連接接入的并發量有高吞吐的性能.

? ? ? ?其實.NET提供了一個非常強大的網絡模型給我們使用,而我們只需要把這個模型用好那基于是不存在多大問題.不過由于很多開發人員對這方面并沒有了解和深入所以感覺.Net編寫一個高效能的服務比較因難.下面通過不同的示例來描述問題的所在從而避免這些問題的出現,讓編寫的服務更高效.

示例1

try {listener.Bind(localEndPoint);listener.Listen(10);// Start listening for connections.while (true) {Console.WriteLine("Waiting for a connection...");// Program is suspended while waiting for an incoming connection.Socket handler = listener.Accept();data = null;// An incoming connection needs to be processed.while (true) {bytes = new byte[1024];int bytesRec = handler.Receive(bytes);data += Encoding.ASCII.GetString(bytes,0,bytesRec);if (data.IndexOf("<EOF>") > -1) {break;}}// Show the data on the console.Console.WriteLine( "Text received : {0}", data);// Echo the data back to the client.byte[] msg = Encoding.ASCII.GetBytes(data);handler.Send(msg);handler.Shutdown(SocketShutdown.Both);handler.Close();}} catch (Exception e) {Console.WriteLine(e.ToString());}

?? ? 這是從MSDN得到的一個服務端示例的代碼地址來源http://msdn.microsoft.com/en-us/library/6y0e13d3(v=vs.110).aspx以上代碼說實話真沒多大的參考意義,不過作為一個演示如何構建一個服務監聽那還是起到作用;用在服務器應用上是完全不可行,因為這只會導致會話串行,同時只能處理一個.接下來在網上找一個支持連接并發的示例看一下

示例2

namespace SocketServer {class Program{private static byte[] result = new byte[1024];private static int myProt = 8885; //端口static Socket serverSocket;static void Main(string[] args){//服務器IP地址IPAddress ip = IPAddress.Parse("127.0.0.1");serverSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);serverSocket.Bind(new IPEndPoint(ip, myProt)); //綁定IP地址:端口serverSocket.Listen(10); //設定最多10個排隊連接請求Console.WriteLine("啟動監聽{0}成功", serverSocket.LocalEndPoint.ToString());//通過Clientsoket發送數據Thread myThread = new Thread(ListenClientConnect);myThread.Start();Console.ReadLine();}/// <summary>/// 監聽客戶端連接/// </summary>private static void ListenClientConnect(){while (true){Socket clientSocket = serverSocket.Accept();clientSocket.Send(Encoding.ASCII.GetBytes("Server Say Hello"));Thread receiveThread = new Thread(ReceiveMessage);receiveThread.Start(clientSocket);}}/// <summary>/// 接收消息/// </summary>/// <param name="clientSocket"></param>private static void ReceiveMessage(object clientSocket){Socket myClientSocket = (Socket)clientSocket;while (true){...int receiveNumber = myClientSocket.Receive(result);Console.WriteLine("接收客戶端{0}消息{1}", myClientSocket.RemoteEndPoint.ToString(), Encoding.ASCII.GetString(result, 0, receiveNumber));}}} }

?? ??? ? 以上示例可以接受多個連接同時進行處理,但缺點是非常明顯如果服務支撐的連接數比較大的情況那這種方式是不可行.你想象一下如果這個服務端要支撐1W,3W或者10W連接的情況那需要開多少個線程去處理這些連接呢,即使可以這樣做那線程的開銷也足夠讓服務器受的了.接下來看MSDN提供的異步示例

示例3

while (true){ // Set the event to nonsignaled state.allDone.Reset();// Start an asynchronous socket to listen for connections.Console.WriteLine("Waiting for a connection...");listener.BeginAccept( new AsyncCallback(AcceptCallback),listener );// Wait until a connection is made before continuing.allDone.WaitOne();}public static void AcceptCallback(IAsyncResult ar) {// Signal the main thread to continue.allDone.Set();// Get the socket that handles the client request.Socket listener = (Socket) ar.AsyncState;Socket handler = listener.EndAccept(ar);// Create the state object.StateObject state = new StateObject();state.workSocket = handler;handler.BeginReceive( state.buffer, 0, StateObject.BufferSize, 0,new AsyncCallback(ReadCallback), state);}

?? ? 這個示例來源于http://msdn.microsoft.com/en-us/library/6y0e13d3(v=vs.110).aspx,其實這個代碼已經非常高效的體現我們在編寫服務的時候如何實現一個接入監聽.此示例用在應用開發上完全勝任的.

改進

????? ? 以上示例3已經提供非常不錯的代碼,那是否可以進行一些規范的改進呢.其實在過往的經驗中來看是可以,首先我們了解.NET有兩種線程,一種是我們常用的而別一種則是IO線程.其實用一些測試工具可以看到AcceptCallback是由IO線程回調,那我們希望回調線程更快速度的釋放出來,那我們需要做一些隔離上的規劃.其實在很多范例代碼中都是一連串地把事件做完,接入->接收->發送.這樣一個連貫性的代碼實現導致后其線程資源的控制和規劃就變得非常因難.???

?

從代碼設計可以通過隊列把回調線程需要的工作隔離出來,可以讓回調線程更快的歸隊來處理其接接入的工作.當隔離后即使以后連接接入需要加一些邏輯控制也不會影響回調線程的快速回歸.這樣就可以讓整個異步線程資源更高效.

public static void AcceptCallback(IAsyncResult ar) {// Signal the main thread to continue.allDone.Set();// Get the socket that handles the client request.Socket listener = (Socket) ar.AsyncState;Socket handler = listener.EndAccept(ar);Queue.Enqueue(handler);}

總結

????? ? 其實隊列分離和控制在整個網絡通訊實施過程會經常用到,其主要作是處理資源的分塊和線程資源控制.畢竟任何一臺服務器的資源都是有限的,如何分配線程資源給不同的任何來完成工作是非常重要,畢竟大量線程的開銷會對系統造成比較大的壓力.

總結

以上是生活随笔為你收集整理的.NET Socket服务编程之-高效连接接入编的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。