真实的国产乱ⅩXXX66竹夫人,五月香六月婷婷激情综合,亚洲日本VA一区二区三区,亚洲精品一区二区三区麻豆

成都創(chuàng)新互聯(lián)網(wǎng)站制作重慶分公司

C#中一個高性能異步socket封裝庫的實現(xiàn)思路分享-創(chuàng)新互聯(lián)

前言

成都創(chuàng)新互聯(lián)是專業(yè)的洪雅網(wǎng)站建設(shè)公司,洪雅接單;提供成都網(wǎng)站設(shè)計、做網(wǎng)站、成都外貿(mào)網(wǎng)站建設(shè)公司,網(wǎng)頁設(shè)計,網(wǎng)站設(shè)計,建網(wǎng)站,PHP網(wǎng)站建設(shè)等專業(yè)做網(wǎng)站服務(wù);采用PHP框架,可快速的進行洪雅網(wǎng)站開發(fā)網(wǎng)頁制作和功能擴展;專業(yè)做搜索引擎喜愛的網(wǎng)站,專業(yè)的做網(wǎng)站團隊,希望更多企業(yè)前來合作!

socket是軟件之間通訊最常用的一種方式。c#實現(xiàn)socket通訊有很多中方法,其中效率最高就是異步通訊。

異步通訊實際是利用windows完成端口(IOCP)來處理的,關(guān)于完成端口實現(xiàn)原理,大家可以參考網(wǎng)上文章。

我這里想強調(diào)的是采用完成端口機制的異步通訊是windows下效率最高的通訊方式,沒有之一!

異步通訊比同步通訊處理要難很多,代碼編寫中會遇到許多“坑“。如果沒有經(jīng)驗,很難完成。

我搜集了大量資料,完成了對異步socket的封裝。此庫已用穩(wěn)定高效的運行幾個月。

縱觀網(wǎng)上的資料,我還沒有遇到一個滿意的封裝庫。許多文章把數(shù)據(jù)收發(fā)和協(xié)議處理雜糅在一塊,代碼非常難懂,也無法擴展。

在編寫該庫時,避免以上缺陷。將邏輯處理層次化,模塊化!同時實現(xiàn)了高可用性與高性能。

為了使大家對通訊效率有初步了解,先看測試圖。

C#中一個高性能異步socket封裝庫的實現(xiàn)思路分享

主機配置情況

C#中一個高性能異步socket封裝庫的實現(xiàn)思路分享

百兆帶寬基本占滿,cpu占用40%,我的電腦在空閑時,cpu占用大概20%,也就是說程序占用cpu 20%左右。

這個庫是可擴展的,就是說即使10萬個連接,收發(fā)同樣的數(shù)據(jù),cpu占用基本相同。

庫的結(jié)構(gòu)圖

C#中一個高性能異步socket封裝庫的實現(xiàn)思路分享

目標(biāo)

即可作為服務(wù)端(監(jiān)聽)也可以作為客戶端(主動連接)使用。

可以適應(yīng)任何網(wǎng)絡(luò)協(xié)議。收發(fā)的數(shù)據(jù)針對字節(jié)流或一個完整的包。對協(xié)議內(nèi)容不做處理。

高可用性。將復(fù)雜的底層處理封裝,對外接口非常友好。

高性能。大限度優(yōu)化處理。單機可支持?jǐn)?shù)萬連接,收發(fā)速度可達幾百兆bit。

實現(xiàn)思路

網(wǎng)絡(luò)處理邏輯可以分為以下幾個部分:

網(wǎng)絡(luò)監(jiān)聽 可以在多個端口實現(xiàn)監(jiān)聽。負責(zé)生成socket,生成的socket供后續(xù)處理。監(jiān)聽模塊功能比較單一,如有必要,可對監(jiān)聽模塊做進一步優(yōu)化。

主動連接 可以異步或同步的連接對方。連接成功后,對socket的后續(xù)處理,與監(jiān)聽得到的socket完全一樣。注:無論是監(jiān)聽得到的socket,還是連接得到的socket,后續(xù)處理完全一樣。

Socket收發(fā)處理 每個socket對應(yīng)一個收發(fā)實例,socket收發(fā)只針對字節(jié)流處理。收發(fā)時,做了優(yōu)化。比如發(fā)送時,對數(shù)據(jù)做了沾包,提高發(fā)送性能;接收時,一次投遞1K的數(shù)據(jù)。

組包處理 一般數(shù)據(jù)包都有包長度指示;比如 報頭的前倆個字節(jié)表示長度,根據(jù)這個值就可以組成一個完整的包。

NetListener 監(jiān)聽

using System;
using System.Net;
using System.Net.Sockets;
using System.Threading;
 
namespace IocpCore
{
 class NetListener
 {
  private Socket listenSocket;
  public ListenParam _listenParam { get; set; }
  public event Action OnAcceptSocket;
 
  bool start;
 
  NetServer _netServer;
  public NetListener(NetServer netServer)
  {
   _netServer = netServer;
  }
 
  public int _acceptAsyncCount = 0;
  public bool StartListen()
  {
   try
   {
    start = true;
    IPEndPoint listenPoint = new IPEndPoint(IPAddress.Parse("0.0.0.0"), _listenParam._port);
    listenSocket = new Socket(listenPoint.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
    listenSocket.Bind(listenPoint);
    listenSocket.Listen(200);
 
    Thread thread1 = new Thread(new ThreadStart(NetProcess));
    thread1.Start();
    
    StartAccept();
    return true;
   }
   catch (Exception ex)
   {
    NetLogger.Log(string.Format("**監(jiān)聽異常!{0}", ex.Message));
    return false;
   }
  }
 
  AutoResetEvent _acceptEvent = new AutoResetEvent(false);
  private void NetProcess()
  {
   while (start)
   {
    DealNewAccept();
    _acceptEvent.WaitOne(1000 * 10);
   }
  }
 
  private void DealNewAccept()
  {
   try
   {
    if(_acceptAsyncCount <= 10)
    {
     StartAccept();
    }
 
    while (true)
    {
     AsyncSocketClient client = _newSocketClientList.GetObj();
     if (client == null)
      break;
 
     DealNewAccept(client);
    }
   }
   catch (Exception ex)
   {
    NetLogger.Log(string.Format("DealNewAccept 異常 {0}***{1}", ex.Message, ex.StackTrace));
   }
  }
 
  private void DealNewAccept(AsyncSocketClient client)
  {
   client.SendBufferByteCount = _netServer.SendBufferBytePerClient;
   OnAcceptSocket?.Invoke(_listenParam, client);
  }
 
  private void AcceptEventArg_Completed(object sender, SocketAsyncEventArgs acceptEventArgs)
  {
   try
   {
    Interlocked.Decrement(ref _acceptAsyncCount);
    _acceptEvent.Set();
    acceptEventArgs.Completed -= AcceptEventArg_Completed;
    ProcessAccept(acceptEventArgs);
   }
   catch (Exception ex)
   {
    NetLogger.Log(string.Format("AcceptEventArg_Completed {0}***{1}", ex.Message, ex.StackTrace));
   }
  }
 
  public bool StartAccept()
  {
   SocketAsyncEventArgs acceptEventArgs = new SocketAsyncEventArgs();
   acceptEventArgs.Completed += AcceptEventArg_Completed;
 
   bool willRaiseEvent = listenSocket.AcceptAsync(acceptEventArgs);
   Interlocked.Increment(ref _acceptAsyncCount);
 
   if (!willRaiseEvent)
   {
    Interlocked.Decrement(ref _acceptAsyncCount);
    _acceptEvent.Set();
    acceptEventArgs.Completed -= AcceptEventArg_Completed;
    ProcessAccept(acceptEventArgs);
   }
   return true;
  }
 
  ObjectPool _newSocketClientList = new ObjectPool();
  private void ProcessAccept(SocketAsyncEventArgs acceptEventArgs)
  {
   try
   {
    using (acceptEventArgs)
    {
     if (acceptEventArgs.AcceptSocket != null)
     {
      AsyncSocketClient client = new AsyncSocketClient(acceptEventArgs.AcceptSocket);
      client.CreateClientInfo(this);
 
      _newSocketClientList.PutObj(client);
      _acceptEvent.Set();
     }
    }
   }
   catch (Exception ex)
   {
    NetLogger.Log(string.Format("ProcessAccept {0}***{1}", ex.Message, ex.StackTrace));
   }
  }
 }
}

另外有需要云服務(wù)器可以了解下創(chuàng)新互聯(lián)scvps.cn,海內(nèi)外云服務(wù)器15元起步,三天無理由+7*72小時售后在線,公司持有idc許可證,提供“云服務(wù)器、裸金屬服務(wù)器、高防服務(wù)器、香港服務(wù)器、美國服務(wù)器、虛擬主機、免備案服務(wù)器”等云主機租用服務(wù)以及企業(yè)上云的綜合解決方案,具有“安全穩(wěn)定、簡單易用、服務(wù)可用性高、性價比高”等特點與優(yōu)勢,專為企業(yè)上云打造定制,能夠滿足用戶豐富、多元化的應(yīng)用場景需求。


當(dāng)前題目:C#中一個高性能異步socket封裝庫的實現(xiàn)思路分享-創(chuàng)新互聯(lián)
網(wǎng)頁地址:http://weahome.cn/article/hpgoe.html

其他資訊

在線咨詢

微信咨詢

電話咨詢

028-86922220(工作日)

18980820575(7×24)

提交需求

返回頂部