【发布时间】:2017-04-22 00:55:07
【问题描述】:
数据包通过NetworkStream从TcpListener发送到TcpClient。数据包不大(5 字节),但频率很高(大约每秒 1000 个或更多)。你能给我建议我应该如何最有效地处理它吗?现在我使用 async 来获取流,填充缓冲区,然后将其剪切到数据包中。之后重复该过程。但
在某些时候我会失去真正的顺序。
s 是 NetworkStream。
数据包有2个字段:type(1 Byte (byte))和value(4 Bytes (int))
MAXVALUEPACKET = 4096
客户代码:
async Task process()
{
bool flag = false;
while (true)
{
byte[] actionBuffer;
flag = false;
actionBuffer = await ReadFromStreamAsync();
while (!flag)
{
byte type = actionBuffer[0];
int value = 0;
if (type > 0)
{
byte[] valueBytes = { actionBuffer[4], actionBuffer[3], actionBuffer[2], actionBuffer[1] };
value = BitConverter.ToInt32(valueBytes, 0);
actionBuffer = actionBuffer.Skip(5).ToArray();
CommonVariables.RawMessages.Add(new KeyValuePair<byte, int>(type, value));
OnHandler();
}
else
flag = true;
}
}
}
byte[] buf = new byte[MAXVALUEPACKET];
async Task<byte[]> ReadFromStreamAsync()
{
await s.ReadAsync(buf, 0, MAXVALUEPACKET);
return buf;
}
【问题讨论】:
-
ReadAsync: "TResult 参数的值包含读入缓冲区的总字节数。结果值可以小于请求的字节数,如果当前可用字节数小于请求数" -
而且,最重要的是,TCP 抽象是字节流。不能保证每次调用
Send都会与另一端调用Receive1-1 匹配。如果您想要“数据包”或“消息”,则由您在 TCP 上实现帧逻辑,或移至更高级别的抽象。 -
@Damien_The_Unbeliever 是的,谢谢!只读5个字节,已经好多了!
标签: c# asynchronous networking