【发布时间】:2012-06-26 14:59:45
【问题描述】:
我一直认为 TcpClient 会简化我的网络应用程序中的套接字操作。
但是,TcpClient 似乎需要知道应该从底层套接字读取多少数据。看起来 TcpClient.GetStream(..).Read(..) 调用 Socket.Receive(..) 读取指定的字节数。
TcpClient 公开了一个 NetworkStream,处理起来可能很烦人。诸如终止字符串和不可靠的 DataAvailable 属性之类的东西使未知 TCP“数据包”的读取变得复杂。
使用 Socket.ReceiveFrom(..) 似乎更面向“数据包”。
我通常使用TcpClient进行绑定和握手等,阅读我使用
Socket socket = _tcpClient.Client;
byte[] buffer = new byte[1000];
IPEndPoint sender = new IPEndPoint(IPAddress.Any, 0);
EndPoint senderRemote = sender;
int length = socket.ReceiveFrom(buffer, ref senderRemote);
string replyString = Encoding.ASCII.GetString(buffer, 0, length);
return replyString;
缓冲区初始化有一些开销,但它比从网络流中一次读取一个字节并查找终止字符或字符串要好。
TcpClient 没有以更好的方式处理读取数据,即 Socket 的方式,是不是有点奇怪?
【问题讨论】:
-
TCP 套接字是数据流,它们不是“基于数据包的”。一端可能会发送一个 32Kb 长的“数据包”,但当它通过 15 个不同的互联网服务器时,1 个数据包现在是 15 个单独的“数据包”,可能需要您调用 15 次接收。如果您没有看到这种行为,那么您还没有进行足够的真实世界测试。
-
@Neil 好吧,这个问题与 TcpClient 而不是 TCP 套接字有关。
-
TcpClient 只是 Socket 的一个包装器,带有一些辅助方法和属性。如果你想使用 Socket,那么没有什么能阻止你(TcpClient.Socket)。 IMO 将 TcpSocket 归咎于“怪异”是误解了 TCP 的实际工作原理。
-
@Neil 我不相信我在责备任何事情或任何人,或者声称 TCP 套接字是基于流的。