C# NET TCP协议的可靠性如何?

C# NET TCP协议的可靠性如何?,c#,.net,networking,tcp,protocols,C#,.net,Networking,Tcp,Protocols,我对C#很陌生,所以请容忍我。我正在用C#.NET4.0编写一个相对简单的客户机-服务器应用程序。更具体地说,我使用TCP协议、TCPListener和TCPClient。我知道TCP协议在理论上是如何工作的。但我必须100%确保在数据传输期间不会出现(未处理的)错误 发送数据后,如何知道数据是否已成功接收。我能完全依赖TCP协议的底层实现吗?所以我没有必要从另一方确认收到了数据 我必须真正了解发送和成功接收了哪些数据,这一点至关重要。 我知道这是一个愚蠢的问题,但我真的想确定。感谢您的时间和回

我对C#很陌生,所以请容忍我。我正在用C#.NET4.0编写一个相对简单的客户机-服务器应用程序。更具体地说,我使用TCP协议、TCPListener和TCPClient。我知道TCP协议在理论上是如何工作的。但我必须100%确保在数据传输期间不会出现(未处理的)错误

发送数据后,如何知道数据是否已成功接收。我能完全依赖TCP协议的底层实现吗?所以我没有必要从另一方确认收到了数据

我必须真正了解发送和成功接收了哪些数据,这一点至关重要。 我知道这是一个愚蠢的问题,但我真的想确定。感谢您的时间和回答。

TCP保证:

  • 您发送的数据将按照您发送的顺序到达
  • 您发送的数据将与您发送的数据完全相同(未修改)
  • 不会收到其他(虚假)数据
它不能保证啮齿类动物不会吃掉你的电缆,大楼的电源将保持接通,甚至当操作系统告诉它某些数据已经到达时,你正在与之交谈的另一台机器上的进程会费心做任何事情

如果您需要确认接收到数据并对其执行操作,则需要手动将确认发送回(因为TCP连接是双工的,您已经有了一个通道来执行此操作)

当然,所有这些都不是特定于.NET、Windows或任何其他网络堆栈实现的


更新:我想特别指出,在操作系统网络堆栈接受数据进行传输之后,您无法知道另一端的进程已经接收到该数据。在大多数情况下,网络堆栈知道数据已到达目标(通过TCP ACK消息),但它不知道目标上的操作系统是否已将数据馈送到目标进程。因此,发送回您自己的“数据已接收并已执行”消息是唯一的选择。

仅使用TCP/IP,您无法确定是否接收到任何数据-您必须在顶部分层另一个协议


如果您可以确定是否收到了某些特定的数据,那么TCP/IP将保证在收到之前所有的数据。

一个选项是通过TCP使用。WCF可靠会话将屏蔽传输故障。

如果您确实需要可靠性和网络传输,为什么不使用消息队列?他们有事务性的保证(大约和使用它的开发人员的纪律一样强,但没有比这更强!)

这就像数据库服务器类型安全性(与性能相同)的所有流量一样。我认为您可以轻松配置


我个人从未这样做过,但我通常使用消息队列。

没有“.NET TCP协议”这样的东西。只有TCP协议,它已经在互联网上运行了大约30年。这是可靠的。这是一个设计目标。

啊,谢谢你的更新,我对这些东西有点困惑。不。如果另一方没有响应,最终操作系统将确定连接已断开并将其关闭。只有尝试写入已关闭的套接字时,才会出现错误。您在连接关闭之前“成功”(就网络堆栈而言)发送的数据将“在传输过程中丢失”。@Ben。是的,异常是您在.NET中确定数据是否正确发送的机制。每当数据未成功发送时(例如使用SendTimeout时断开连接或超时),就会引发
SocketException
。@MarkH:这不是真的。阅读Socket文档中的最后一段备注。我假设这只是非阻塞套接字的情况。只有一种TCP。好吧,只要你知道这是一个“愚蠢的问题”,我在这里的工作就完成了。如果您想说得更具体一些,那么您应该说您希望确保在TCPListener和TCPClient的.NET实现中,以及您正在使用的任何其他类中,不会出现未经处理的错误,因为这几乎是验证一切正常工作所能做到的。True。我(重新)将他的问题的这一部分解释为TCP协议的.NET实现,因为TCP实现在细节上确实不同(如
TIME\u WAIT
timeout等的默认值),谁知道这会如何影响可靠性?