当SOCKET传送数据的时候,一般来说,你需要构建自己的消息体,比如,我的消息体是如下定义的: 
消息类型-消息长度-消息本身 
这样,你在取数据的时候,就可以取到很确切的消息长度,接收方根据这个长度去获取消息本身就行。 
如下代码段: 
                  recv = _currentSocket.Receive(dataType, 0, 4, 0); 
                if (recv == 0) 
                    throw new Exception("receive dataType broken."); 
                recv = _currentSocket.Receive(datasize, 0, 4, 0); 
                if (recv == 0) 
                    throw new Exception("receive dataSize broken."); 
                int size = BitConverter.ToInt32(datasize, 0); 
                int dataleft = size;                 byte[] data = null; 
                if (Encoding.ASCII.GetString(dataType, 0, recv) == "data") 
                { 
                    data = new byte[size]; 
                    while (total < size) 
                    { 
                        recv = _currentSocket.Receive(data, total, dataleft, 0); 
                        if (recv == 0) 
                            throw new Exception("receive data broken."); 
                        total += recv; 
                        dataleft -= recv; 
                    } 
                    total = 0; 
                    dataleft = 0; 
                    _receivedData(_connectIndex, Encoding.ASCII.GetString(data)); 
                    Debug.Print("data = " + Encoding.ASCII.GetString(data)); 
                } 
先获取dataType,再获取datasize,继而获取data本身,具体参考下面的博文 本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/luminji/archive/2008/12/25/3606072.aspx

解决方案 »

  1.   

    加lock 
     private static readonly object objLock = new object();lock(objlock)
    {
       //接受的方法
    }
      

  2.   

    他这种情况应该是在网络不稳定时候发生,所以设一个接收TIMEROUT就应该可以解决
      

  3.   

    楼主参考一下TCP如何建立可靠的连接吧,你可以实现一个简化版本。
      

  4.   

    http://www.cnblogs.com/JimmyZhang/archive/2008/09/16/1291854.html
    自己去看吧,
      

  5.   

    。设置一个TIMEROUT,触发异常时重新发送和接收,不就OK了?建议不要用异步接收,难控件,我做过一个后来全改为倾听连接后开一个线程,接收其它数据而不使用异步接收
      

  6.   

    当SOCKET传送数据的时候,一般来说,你需要构建自己的消息体,比如,我的消息体是如下定义的: 
    消息类型-消息长度-消息本身 
    这样,你在取数据的时候,就可以取到很确切的消息长度,接收方根据这个长度去获取消息本身就行。 
    如下代码段: 
                      recv = _currentSocket.Receive(dataType, 0, 4, 0); //1
                    if (recv == 0) 
                        throw new Exception("receive dataType broken."); 
                    recv = _currentSocket.Receive(datasize, 0, 4, 0); //2                if (recv == 0) 
                        throw new Exception("receive dataSize broken."); 
                    int size = BitConverter.ToInt32(datasize, 0); 
                    int dataleft = size;                 byte[] data = null; 
    实际操作过程中 红色1和红色2存在问题:
    1.当发送端发送完第一次数据后,  触发红1动作,但如果发送端马上发送第二次数据,由于接收端还没有开启第二次接收,这样数据包就会丢失,或者红1动作后处理数据过慢,而发送端还在不停地发送数据包,那红2就会接收到多次发送的数据包,所以在发送数据时要控制好时间,我的方法是每接收到一次数据包处理完后开启第二次接收同时发送确认数据包到发送端,发送端收到确认包后才发送数据。
    Dim ReceMsgtemp() As Byte = Encoding.UTF8.GetBytes("Rcomplit")
     Dim lint As Integer = newsocket.Receive(snbyte, 1024, SocketFlags.None)
                    If lint > 0 Then
                        sn = Encoding.UTF8.GetString(snbyte, 0, lint)
                        end If
    Dim computconfigbyte(1024) As Byte
    newsocket.Send(ReceMsgtemp)
     lint = newsocket.Receive(computconfigbyte, 1024, SocketFlags.None)
                    If lint > 0 Then
                        computconfigtemp = Encoding.UTF8.GetString(computconfigbyte, 0, lint)
                        computconfig += computconfigtemp
                    End If