C# 指示所有数据已通过网络接收的最佳方式?
我有一个运行良好的客户机/服务器应用程序,但它缺少一个关键的行为,使其更加可靠 目前,就网络能力而言,它还远远不够“强大”。我正试图实现这一目标,研究使我相信,我需要某种协议,以确保在网络传输过程中不会丢失任何数据 我听说过几种方法。我认为对我们的情况最有效的一种方法是使用终止符,类似于C# 指示所有数据已通过网络接收的最佳方式?,c#,networking,tcp,tcpclient,tcplistener,C#,Networking,Tcp,Tcpclient,Tcplistener,我有一个运行良好的客户机/服务器应用程序,但它缺少一个关键的行为,使其更加可靠 目前,就网络能力而言,它还远远不够“强大”。我正试图实现这一目标,研究使我相信,我需要某种协议,以确保在网络传输过程中不会丢失任何数据 我听说过几种方法。我认为对我们的情况最有效的一种方法是使用终止符,类似于标记。我的问题是,我不确定实现这一点的最佳方式 这里有几个代码片段,在找到最佳解决方案后,我将对它们进行修改,以包含一个终止符 客户: TcpClient client = new TcpClient(); c
标记。我的问题是,我不确定实现这一点的最佳方式
这里有几个代码片段,在找到最佳解决方案后,我将对它们进行修改,以包含一个终止符
客户:
TcpClient client = new TcpClient();
client.Connect(hostname, portNo);
using (var stream = client.GetStream())
{
//send request
stream.Write(data, 0, data.Length);
stream.Flush();
//read server response
if (stream.CanRead)
{
byte[] buffer = new byte[1024];
string response = "";
int bytesRead = 0;
do
{
bytesRead = stream.Read(buffer, 0, buffer.Length);
response += Encoding.ASCII.GetString(buffer, 0, bytesRead);
} //trying to replace 'DataAvailable', it doesn't work well
while (stream.DataAvailable);
}
}
注意,我试图替换检查流中更多数据的stream.DataAvailable
方法。它一直在制造问题
服务器:
var listener = new TcpListener(IPAddress.Any, portNo);
listener.Start();
var client = listener.AcceptTcpClient();
using (var stream = client.GetStream())
{
var ms = new System.IO.MemoryStream();
byte[] buffer = new byte[4096];
int bytesRead = 0;
do
{
bytesRead = stream.Read(buffer, 0, buffer.Length);
ms.Write(buffer, 0, bytesRead);
} //also trying to replace this 'stream.DataAvailable'
while (stream.DataAvailable);
ms.Position = 0;
string requestString = Encoding.UTF8.GetString(ms.ToArray());
ms.Position = 0;
/*
process request and create 'response'
*/
byte[] responseBytes = Encoding.UTF8.GetBytes(response);
stream.Write(responseBytes, 0, responseBytes.Length);
stream.Flush();
}
因此,给定这两个代码示例,我如何修改它们以包括并检查某种数据终止符,该终止符指示停止读取数据是安全的?您可以依靠TCP在FIN之前传输所有数据。代码的问题是available()不是流结束的有效测试。这是对现有数据的测试 因此,您过早地终止了读取循环,从而在接收方丢失了数据,在发送方得到了重置 您应该只阻塞Read()方法,直到从API收到EOS指示,无论C#中是什么 您不需要自己额外的EOS指示器。我们在项目的两端都使用了EOS(流结束)指示器。我不会发布完整的代码示例,但这里有一个关于其工作原理的小片段:
stream.Write(data, 0, data.Length);
stream.WriteByte(Convert.ToByte(ConsoleKey.Escape));
stream.Flush();
在该流的接收端,循环逐字节读取数据。一旦它接收到
ConsoleKey.Escape
字节,它就会终止循环。它起作用了 不使用http有什么具体原因吗?是的,但这有点无关紧要。我不想在这里讨论这个问题。所以我想你想要流媒体和开放式的连接?不一定。服务器应用程序是多线程的,总是在侦听,并在完成处理后关闭每个连接。我也不太清楚这是怎么回事,因为它与数据本身无关。TCP是否已经确保了“在连接到局域网、内部网或公共互联网的计算机上运行的程序之间可靠、有序、经错误检查的八位字节流的传递。”()。这是UDP协议吗?