Socket 异步接收 缓冲区发生改变
采用异步发送和接收的方式。
发送代码
public void ASend(string Name,byte[] Content,int size)
{
if (mSocket == null)
throw new ArgumentNullException("连接不存在");
if (Content == null)
return;
MyTreaty my = new MyTreaty(Name, Content,size);
byte[] SendData = my.GetBytes();
try
{
//先得到数据包的长度
int len = SendData.Length;
//把数据包的长度写入byte数组中
byte[] head = BitConverter.GetBytes(len);
byte[] newByte = new byte[head.Length + len];
Array.Copy(head, 0, newByte, 0, head.Length);
Array.Copy(SendData, 0, newByte, 4, len);
mSocket.BeginSend(newByte, 0, newByte.Length, 0, new AsyncCallback(SendCallBack), mSocket);
}
catch(Exception ex)
{
}
}
private void ReceiveCallback(IAsyncResult ar)
{
try
{
//
StateObject state = ar.AsyncState as StateObject;
//读取数据
int bytesRead = mSocket.EndReceive(ar);
if (bytesRead > 0)
{
byte[] head = new byte[4];
Array.Copy(state.buffer, 0, head, 0, 4);
//计算包头的长度
int length = BitConverter.ToInt32(head, 0);
byte[] data = new byte[length];
Array.Copy(state.buffer, 4, data, 0, length);
MyTreaty my = MyTreaty.GetMyTreaty(data);
if (onStreamData != null)
onStreamData(my);
Thread.Sleep(10);
mSocket.BeginReceive(state.buffer, 0, StateObject.BufferSize, 0, new AsyncCallback(ReceiveCallback), state);
}
}
catch (SocketException se)
{
if (onClosed != null)
onClosed(ID, se.Message);
}
catch (Exception e)
{
throw new ApplicationException(e.Message);
}
}
按你现在的接收逻辑,
int bytesRead = mSocket.EndReceive(ar);
此时整个包必须收全才能正确的收下一个包,
因为你默认下一次收到的是下一个包头。
若是包不全,下一次收到的是包第二部份, 你的程序就错了。
可以自定义一个协议 规定一个 Head 跟 Food (不对英文的正确性负责)
然后一条一条的放到队列里。一条处理完 再处理下一条!
如果我用阻塞式发送,发完一张再接着发下一张,局域网socket传输效率能满足我投影桌面的要求吗?