华为q2s-win7 activation v1 7

socket error
2023年4月3日发(作者:平板和笔记本区别)

Socket套接字连接状态判断,接收数据笔记

最近⼯作中涉汲到⼀些Socket⽅⾯应⽤,如断线重连,连接状态判断等,今天做了⼀些总结。

1.判断Socket连接状态

通过Poll与Connected结合使⽤,重点关注SelectRead模式

⽅法名:

(intmicroSeconds,Modemode)⽅法参数:

参数枚举:

SelectRead如果已调⽤Listen(Int32)并且有挂起的连接,则为true。-或-如果有数据可供读取,则为true。-或-如果连接已关闭、重置

或终⽌,则返回true;否则,返回false。

SelectWrite如果正在处理Connect(EndPoint)并且连接已成功,则为true;-或-如果可以发送数据,则返回true;否则,返回false。

SelectError如果正在处理不阻⽌的Connect(EndPoint),并且连接已失败,则为true;-或-如果OutOfBandInline未设置,并且带外数据

可⽤,则为true;否则,返回false。

SelectRead模式返回true的三种情况,若Socket处挂起状态,同时没有数据可读取,可以确定Socket是关闭或终⽌的。

1.已调⽤Listen(Int32)并且有挂起的连接,则为true

2.有数据可供读取,则为true

3.如果连接已关闭、重置或终⽌,则返回true

如下代码,true表⽰连接断开

(1000,Read)&&(ble==0)||!ted

稍作调整,判断连接状态完整代码如下:

publicstaticboolIsSocketConnected(Sockets)

{

#regionremarks

/*Aszendarwrote,ble,butyouneedtotakeintoconsideration

*thatthesocketmightnothavebeeninitializedinthefirstplace.

*Thisisthelast(Ibelieve)tedproperty.

*Therevisedversionofthemethodwouldlookssomethinglikethis:

*from:/questions/2661764/how-to-check-if-a-socket-is-connected-disconnected-in-c*/

#endregion

#region过程

if(s==null)

returnfalse;

return!(((1000,Read)&&(ble==0))||!ted);

/*Thelong,butsimpler-to-understandversion:

boolpart1=(1000,Read);

boolpart2=(ble==0);

if((part1&&part2)||!ted)

returnfalse;

else

returntrue;

*/

#endregion

}

Blocking属性

默认情况Blocking为true,即阻塞状态,Read时若没收到数据,Socket会挂起当前线程,直到收到数据,当前线程才被唤醒。适⽤于接收

到数据完成后再进⾏下⼀步操作场景。反之Blocking为false,调⽤Recevied后,⽆论是否收到数据,都⽴即返回结果,当前线程可以继

续执⾏。

MSDN强调,Blocking属性值与异步操作如(Begin开始API)BeginReceive等没有相关性,⽐如通过BeginReceive接收数据,同时希望

当前线程挂起,看起来,似乎可将Blocking设为true实现。其实不然,需要通过信号量ManualResetEvent实现挂起操作。

resendingandreceivingdataasynchronouslyandwanttoblockexecution,

usetheclass

发送数据时,⾃动断线重连

如添加⼼跳机制。这⾥另⼀个简单⽅案,在发送数据时,检查连接状态,如发现断开,重新建⽴连接,这⾥Socket操作加了锁,防⽌并发

操作。

publicstaticboolSendServer(stringst)//发送

{

lock(SocketLock)

{

try

{

if(SocketClient==null||!ted){

//断开连接

if(SocketClient!=null)

CloseSocket(SocketClient);

//重新连接

if(!onnect(,)){

returnfalse;

}

}

tchwatch=tch();

();

byte[]Msg=es(st);

(Msg);

//接收相机返回结果

byte[]bytResult;

Receive(SocketClient,socketBuffer,0,EndMathFormat,eTimeout,outbytResult);

();

("获取相机坐标信息耗时(ms):"+dMilliseconds);

stringReciveMsg=ing(bytResult).TrimEnd(newchar[]{'n','0'});

Msg=ReciveMsg;

=ReciveMsg;

ew((s)=>{MyEvent(ng());},ReciveMsg);

returntrue;

}

catch(Exceptionex)

{

(ex,"发送消息给相机⽤来切换功能异常");

if(!IsSocketConnected(SocketClient))

{

//断开连接

CloseSocket(SocketClient);

//重新连接

onnect(,);

}

}

returnfalse;

}

}

接收数据场景

通常两种场景,如:

a.接收指定长度数据包。

b.接收不定长数据包,根据终⽌符结束。(不定长数据包以末尾n0做为结束标记,本⽰例可能返回包含多条终⽌符数据,需对结果⼆

次分隔,如abcn0defn0)

=>定长数据包接收:

///

///socket接收定长数据

///

///

///

///

///

///

publicstaticvoidReceive(Socketsocket,byte[]buffer,intoffset,intsize,inttimeout)

{

intendTickCount=unt+timeout;

intreceived=0;//howmanybytesisalreadyreceived

interrTimes=0;

do

{

if(unt>endTickCount)

thrownewException("ReceiveTimeout.");

try

{

received+=e(buffer,offset+received,size-received,);

}

catch(SocketExceptionex)

{

if(ErrorCode==lock||

ErrorCode==ing||

ErrorCode==erSpaceAvailable)

{

if(++errTimes>3)

thrownewException("ReceiveerrTimes引发异常");

//socketbufferisprobablyempty,waitandtryagain

(30);

}

else

throwex;//anyseriouserroroccurr

}

}while(received

}

=>不定长数据包接收:

publicstaticvoidReceive(Socketsocket,byte[]buffer,intoffset,byte[]endMath,inttimeout,outbyte[]bytResult)

{

intendTickCount=unt+timeout;

intreceived=0;//howmanybytesisalreadyreceived

intsize=;

boolisMatch=false;

interrTimes=0;

intj=0;

do

{

if(unt>endTickCount)

thrownewException("ReceiveTimeout.");

try

{

received+=e(buffer,offset+received,size-received,);

isMatch=true;

j=0;

for(inti=;i=0;i++)

{

if(buffer[i]!=endMath[j++])

{

isMatch=false;

break;

}

}

if(isMatch)

{

break;

}

if(received>=size)

{

thrownewException("Receive结束符⾮预期!");

}

}

catch(SocketExceptionex)

{

if(ErrorCode==lock||

ErrorCode==ing||

ErrorCode==erSpaceAvailable)

{

if(++errTimes>3)

thrownewException("ReceiveerrTimes引发异常");

//socketbufferisprobablyempty,waitandtryagain

(30);

}

else

throwex;//anyseriouserroroccurr

}

}while(true);

bytResult=newbyte[received];

(buffer,0,bytResult,0,received);

}

5.关闭Socket

privatestaticvoidCloseSocket(Socketsocket)

{

try

{

if(socket!=null)

{

wn();

();

}

}

catch(Exceptionex)

{

(ex,"关闭socket时发⽣异常:"+e);

}

finally{

socket=null;

}

}

更多推荐

socket error