.net C# 異步Socket 發送類.


採用異步Socket發送時,對於對像的回收使用了池技術

   /// <summary>
    /// 用於輔助異步發送Socket的幫肋類
    /// </summary>
    public class AsyncSocketSendHelper
    {

        #region 客戶端聯接池
        /// <summary>
        /// 接收SAEA池集合
        /// </summary>
        private ConcurrentStack<SocketAsyncEventArgs> ReceiveSocketArgsPool = new ConcurrentStack<SocketAsyncEventArgs>();

        /// <summary>
        /// 初始化接收socketargs對象池
        /// </summary>
        protected void InitReceiveSocketArgsPool()
        {
            for (int ndx = 0; ndx < 3000 ; ndx++)
            {
                ReceiveSocketArgsPool.Push(CreateReceiveSocketArgs());
            }
        }

        /// <summary>
        /// 創建一個接收SAEA對象,設置最大接收字節數
        /// </summary>
        /// <returns></returns>
        protected virtual SocketAsyncEventArgs CreateReceiveSocketArgs()
        {
            SocketAsyncEventArgs e = new SocketAsyncEventArgs();
            e.Completed += IO_SendComleted;
            return e;
        }




        /// <summary>
        /// 租賃一個接收SAEA對象
        /// </summary>
        /// <returns></returns>
        protected virtual SocketAsyncEventArgs RentReveiveSocketArgs()
        {
            SocketAsyncEventArgs e;

            return ReceiveSocketArgsPool.TryPop(out e) ? e : CreateReceiveSocketArgs();
        }

        /// <summary>
        /// 歸還一個接收SAEA參數
        /// </summary>
        /// <param name="e">還池</param>
        protected virtual void GivebackReceiveSocketArgs(SocketAsyncEventArgs e)
        {
            if (e != null)
            {
                e.UserToken = null;
                ReceiveSocketArgsPool.Push(e);
            }
        }

        #endregion

        /// <summary>
        /// 發送數據服務
        /// </summary>
        /// <param name="socket">用於發送的Socket對像</param>
        /// <param name="buff">需要發送的數據</param>
        /// <param name="callBack">回調函數參數爲:發送結果,目標節點,發送數據</param>
        /// <param name="userToken">用戶數據 </param>
        /// <returns></returns>
        public virtual void SendToAsync(Socket socket, byte[] buff, Action<AsyncSendResult> callBack = null, object userToken = null)
        {
            if (socket == null)
            {
                throw new NullReferenceException();
            }

            if (buff == null)
            {
                throw new NullReferenceException();
            }

            SocketAsyncEventArgs e = RentReveiveSocketArgs();
            //設置發送緩衝區
            e.SetBuffer(buff, 0, buff.Length);
            try
            {
                //用戶標識
                var token = new AsyncSendResult
                {
                    Result = false,
                    RemoteEndPoint = socket.RemoteEndPoint.ToString(),
                    SendTime = DateTime.Now,
                    SendData = buff,
                    ResultTime = DateTime.Now,
                    CallBakc = callBack,
                    UserToKen = userToken,
                };
                e.UserToken = token;
                //發送數據
                if (!socket.SendAsync(e))
                {
                    IO_SendComleted(socket, e);
                }
            }
            catch (SocketException)
            {
                //還池
                GivebackReceiveSocketArgs(e);
            }
            catch (ObjectDisposedException)
            {
                //還池
                GivebackReceiveSocketArgs(e);
            }
        }

        /// <summary>
        /// 發送數據後的完成功能
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        protected virtual void IO_SendComleted(object sender, SocketAsyncEventArgs e)
        {
            try
            {
                if (e.UserToken != null)
                {
                    AsyncSendResult token = e.UserToken as AsyncSendResult;
                    if (token != null)
                    {
                        //設置結果時間
                        token.ResultTime = DateTime.Now;

                        //發送數據OK
                        if (e.SocketError == SocketError.Success)
                        {
                            token.Result = true;
                            if (token.CallBakc != null)
                            {
                                token.CallBakc(token);
                            }

                        }
                        else
                        {
                            //發送數據失敗
                            token.Result = false;
                            if (token.CallBakc != null)
                            {
                                token.CallBakc(token);
                            }
                        }
                    }
                }
            }
            finally
            {
                //還池
                GivebackReceiveSocketArgs(e);
            }
        }






    }

    /// <summary>
    /// 異步發送結果
    /// </summary>
    public class AsyncSendResult
    {
        /// <summary>
        /// 結果
        /// </summary>
        public bool Result { get; set; }

        /// <summary>
        /// 目標節點
        /// </summary>
        public string RemoteEndPoint { get; set; }

        /// <summary>
        /// 發送數據
        /// </summary>
        public byte[] SendData { get; set; }

        /// <summary>
        /// 發送時間
        /// </summary>
        public DateTime SendTime { get; set; }

        /// <summary>
        /// 結果返回時間
        /// </summary>
        public DateTime ResultTime { get; set; }


        /// <summary>
        /// 獲取或設置與此操作關聯的用戶或應用程序對象。
        /// </summary>
        public object UserToKen { get; set; }

        /// <summary>
        /// 用於回調的委託
        /// </summary>
        internal Action<AsyncSendResult> CallBakc { get; set; }
    }



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章