SocketAsyncEventArgs使用解说

原文:SocketAsyncEventArgs使用解说

        如果在.NET下写过网络通讯的同学应该感觉不陌生了,有很多刚入门的同学很多都认为这东西可以大大提高处理效能还有就是使用上很不适应.其实使用之前最好通过MSDN了解一下,该对象紧紧是Begin End模式的一个增强版本,它的主要作用主要是解决之前异步过程时创建不可复用的异步对象而产生的.主要是在高并发下节省大量对象重分配和同步相关问题,从而实现在高并发吞吐下更少的资源损耗(如果你的应用紧紧是密集通讯那性能提供相对来说是可观一点,但应用还存在其他处理那就不要想着它能有质的改变了).

       SocketAsyncEventArgs(SAEA)在.net 2.0 sp1所提供开发人员主要使用它的场景分别是Accept,Send和Receive.在传统的Begin End模式中一般都通过调用Begin方法然后在回调方法中调用End来处理,其实SAEA原理差不多,只是由原来的指定的回调过程变成了完成事件,更重要的一个改变就是SAEA是可以复用的.下面详解一下SAEA的以上几种用法.

主要属性和事件

    在使用SocketAsyncEventArgs进行TCP或UDP通讯的时候最常用的几个成员分别是:Buffer,BufferList,BytesTransferred,SocketError,UserToken,BytesTransferred属性,SetBuffer方法和Completed事件。

    SocketAsyncEventArgs接收和发送数据都需要设置buffer,一般用SetBuffer方法或设置BufferList。通过Completed来查看完成情况,而在Completed通过SocketError和BytesTransferred结合来判断当前操作是否成功能,如在receive状态当BytesTransferred为零的时候,说明对方已经把连接断开了。

    由于SocketAsyncEventArgs是异步操作,在很多情况需要的一些其他信息传递到Completed事件中,这个时候可以通过UserToken属性来解决异步信息传递的问题。

使用注意:SocketAsyncEventArgs同一时间只能进行一个操作,通过Completed来确认当前操作是否完成,如果同步完成是不会触该事件需要自己手动调用处理。

Accept

此方法是管连接接入,一般在写TCP应用的的时候需要用到(UDP下则不需要).

if(!Socket.AcceptAsync(saea))
{
    Accept_Process(Socket,saea);
}

    在使用的时候一般是采用以上方法,如果是同步完成就手动调用完成处理过程,否则会触发完成事件.所以在构建saea的时候必须绑定Competed事件,也可以通过承继saea类派生OnCompleted方法处理也行.

private void Accept_Process(object sender,SocketAsyncEventArgs e)
{
       if (e.SocketError == SocketError.Success)
       {
            //成功
       }
       else
       {
            ReleaseSocket(e.AcceptSocket);
       }
       Accept();
}

    可以通过判断SocketError来确定连接接入是否成功,如果方法还要处理一些有可能存在异常的逻辑,那这里最好写上try catch.防止在线程回调过程出现未知异常导致服务关闭的严重问题发生. 在使用SAEA进行Accept的时候其实也可以设置buffer,这个的主要作用是当连接接入后必须收到对方请求的数据才会触发完成事件.

Send

在Socket针对SAEA的Send操作用两个分别是SendAsync和SendToAsync,前者是基于有连接状态常用于TCP,而后者则用于无连接状态的一般发送UDP的时候使用.

if (!mSocket.SendAsync(mSendSAEA))
                        {
                            OnSend(this, mSendSAEA);
                        }

发送方法返回一个布尔值,如果为false则为同步完成需要手动调用完整事件对应的方法;数据的发送情况同样通过SAEA的完成事件来处理.

 private void OnSend(object sender, System.Net.Sockets.SocketAsyncEventArgs e)
        {
            if (e.SocketError == System.Net.Sockets.SocketError.Success )
            {
              //成功
            }
            else
            {
               // Dispose();
            }
        }

    在完成事件通过SockeError来判断发送是否成功,如果不成功那基本上就说明当前连接出现异常,可以对当前TCP连接断开.实际还有几种状态需要考虑如 IOPending,不过在发关数据的时候是单一投递则不会存在这情况 .在传统的begin,end模式中需要判断发送字节数量的情况,而在SAEA中则不需要.

Receive

接收和发送的原理基本一致.

if (!mSocket.ReceiveAsync(mReceiveSAEA))
{
      OnReceive(this, mReceiveSAEA);
}
        private void OnReceive(object sender, System.Net.Sockets.SocketAsyncEventArgs e)
        {
            if (e.SocketError == System.Net.Sockets.SocketError.Success && e.BytesTransferred > 0)
            {
                //数据接收成功

                BeginReceive();
            }
            else
            {
                                Dispose();
            }
        }

注意

    在Win下SocketAsyncEventArgs绑定Buffer或BufferList都是需要注意,尽可能绑定同一份byte[]的引用,如果不是会导致内部缓存区重新绑定影响性能,Mono下从源代码来看是不会有这情况发生.在一些交流中经常碰到如何用SAEA实现双功,其实网络通讯中只有输入和输出,不存在只是单向的概念,对于SAEA同一时间只能允许一个操作,所以在做应用的时候需要同时接收和发送则可以针对发和收都单独定义个SAEA即可.如果为了更好地利用做个SAEA Pool则相对来说比较好.

时间: 2024-09-01 21:48:06

SocketAsyncEventArgs使用解说的相关文章

javascript事件列表解说

javascript 事件 浏览器支持 解说 一般事件 onclick IE3.N2 鼠标点击时触发此事件 ondblclick IE4.N4 鼠标双击时触发此事件 onmousedown IE4.N4 按下鼠标时触发此事件 onmouseup IE4.N4 鼠标按下后松开鼠标时触发此事件 onmouseover IE3.N2 当鼠标移动到某对象范围的上方时触发此事件 onmousemove IE4.N4 鼠标移动时触发此事件 onmouseout IE4.N3 当鼠标离开某对象范围时触发此事件

新站SEO方案解说——网站定位

新站SEO方案却是许多人头痛的话题,我们才刚学习SEO,不知道怎么写,或者我们已经有优化过成功的站点,都是自己未写过SEO方案之类的东西.许多人对于SEO方案都存在疑问,我们们为什么要书写SEO方案.大家都知道SEO是干嘛,SEO是搜索引擎的优化,而我们们的做站主要是为什么,为不是就是把关键词排名做上去,为的不就是把网站的排名搞上去了,让用户搜索某一个关键词进入我们们的网站,从而把我们们网站的服务或者产品销售出去,达到关键词排名与网站盈利最大利益化吗. 但是对于新站来说,SEO方案起着什么作用呢

王克江:解说网站导航如何优化 考虑用户体验和标准化设计

网站导航作为网站优化的重点应该有具体的操作方法,导航关键词如何的布局,栏目URL如何设计都需要根据用户体验原则谨慎考虑,下面idsem团队王克江为大家具体解说: 一.网站导航关键词的布局应遵循网站最初的策划理念,网站的定位决定了网站以后的发展方向. 1.门户或者品牌网站的策划定位 1).网站的行业定位 如果您网站定位为行业网站,那么网站导航的关键词的布局应考虑行业的目前现状,网站导航的关键词布局是核心词布局还是目标关键词布局要根据行业的特色做具体的调查,调查的方向应着手数据分析.人群分析.市场分

王克江:详细案例解说百度中文分词原理

搜索引擎算法的改变迎来的中文分词原理的变化,下面idsem团队成员王克江以中文分词原理来解说百度中文分词原理的分词规则,分享如下: 一.中文分词原理的解说 1.基于理解的分词方法 基于理解的分词方法就是机器模拟人来理解词语,在语言知识及其词库的配合下,机器执行语句控制,词意控制,以及分词控制来模拟人来读取网页信息.可以理解成机器模拟人分词. 2.基于字符串匹配的分词方法 基于字符串匹配分词是与词库进行对比按照不同的扫描方式进行分词,扫描方式分为四种: 1)正向最大匹配法(由左到右的方向) 2)逆

深入继承之抽象类和接口综合分析及完整案列解说(二)

通过深入继承之抽象类和接口综合分析及完整案列解说(一),我想大家已经认识到了知识共享的巨大力量了.我门上面看到的这些东西不 是我们任何一个人在短时间内就能够总结出来的,但是大家一起总结,那结果就是这样爽的. 我希望大家都能够大方一点,别做得那么 小气,生怕自己知道的那点知识被别人知道了.饭碗就被别人抢了,事实上在跟人分享的过程中并不是一味的在付出,你同样也会有收获,无 论是帮别人解答疑问还是跟别人交流,就好象我在写(或着说我是在复制别人的心得)一样,看起来我是在无偿的为大家做,事实上呢我同样 的

解说Win32的窗口子类化

也许你需要一个特殊的Edit来限制浮点数的输入,但是现有的Edit却并不能完成这项工作--因为它只能够单纯的限制大小写或者纯数字.当你在论坛上求救的时候,某个网友告诉你:"用子类化."你也许会在看到一线曙光的同时多出了一连串的问题:何为子类化?子类化的原理是什么?如何实现子类化?下面就让我从一个简单的C++程序开始,一步步解开你的疑团吧. 首先,我为你列出以下这个C++程序: #include <iostream> using namespace std; class Pa

使用.net3.5的缓存池和SocketAsyncEventArgs类创建socket服务器

在.NET 3.5里System.Net.Sockets空间下有一组增强功能的类,提供可供专用的高性能套接字应用程 序使用的可选异步模式,SocketAsyncEventArgs 类就是这一组增强功能的一部分.该类专为需要高性能 的网络服务器应用程序而设计.应用程序可以完全使用增强的异步模式,也可以仅仅在目标热点区域(例 如,在接收大量数据时)使用此模式.以下是关于此类的介绍(摘自MSDN) http://msdn.microsoft.com/zh-cn/library/system.net.s

kk录像机怎么录制CF解说视频

kk录像机怎么录制CF解说视频          第一步:下载CF视频录制工具 首先下载KK录像机,下载完毕直接安装运行. 打开KK录像机,录制模式选择全屏模式,如果你的CF游戏是窗口化的,那么录制模式要选择区域模式,并把录制区域调整到CF游戏窗口大小.Win7.Win8.Win10系统可以直接选择帧率模式,进入游戏后,游戏画面左上角有黄色帧率数字跳动. 第二步:开始录制CF视频 现在可以开始录制了,不过CF游戏在房间选人阶段的画面分辨率是1024x768,很多玩家设置的游戏辨率不是1024x7

曝DOTA著名解说2009伍声淘宝网店年入千万

&http://www.aliyun.com/zixun/aggregation/37954.html">nbsp;   以解说和职业选手两个身份都取得了巨大的成功,这就是伍声的特别之处.放眼电子竞技领域的其它知名人物,多以单一身份成名,但像伍声这样作为选手拿到世界冠军,退役转行解说也获得不俗成就的人确实很少.在职业巅峰时期他看到了解说的巨大前景,急流勇退并先人一步利用淘宝把自己的名声变现,证明了他的头脑. 伍声是一个头脑清醒的人,敢于拼搏并知道自己要做什么,仅凭这一点他就远远超过