如何从NetworkStream获取所有数据

我试图读取通过TCP/IP连接的机器缓冲区中存在的所有数据,但我不知道为什么我没有得到所有数据,一些数据正在错过。 这是我正在使用的代码..

 using (NetworkStream stream = client.GetStream()) { byte[] data = new byte[1024]; int numBytesRead = stream.Read(data, 0, data.Length); if (numBytesRead > 0) { string str= Encoding.ASCII.GetString(data, 0, numBytesRead); } } 

请告诉我我缺少什么来从机器获取所有数据。 提前致谢..

您的代码的问题是,如果数据大小大于缓冲区大小(在您的情况下为1024字节),则不会获得所有数据,因此您必须读取循环内的流。 然后,您可以Write所有数据Write MemoryStream直到NetworkStream结束。

  string str; using (NetworkStream stream = client.GetStream()) { byte[] data = new byte[1024]; using (MemoryStream ms = new MemoryStream()) { int numBytesRead ; while ((numBytesRead = stream.Read(data, 0, data.Length)) > 0) { ms.Write(data, 0, numBytesRead); } str = Encoding.ASCII.GetString(ms.ToArray(), 0, (int)ms.Length); } } 

MSDN中的此示例:NetworkStream.DataAvailable显示了如何使用该属性执行此操作:

 // Examples for CanRead, Read, and DataAvailable. // Check to see if this NetworkStream is readable. if(myNetworkStream.CanRead) { byte[] myReadBuffer = new byte[1024]; StringBuilder myCompleteMessage = new StringBuilder(); int numberOfBytesRead = 0; // Incoming message may be larger than the buffer size. do{ numberOfBytesRead = myNetworkStream.Read(myReadBuffer, 0, myReadBuffer.Length); myCompleteMessage.AppendFormat("{0}", Encoding.ASCII.GetString(myReadBuffer, 0, numberOfBytesRead)); } while(myNetworkStream.DataAvailable); // Print out the received message to the console. Console.WriteLine("You received the following message : " + myCompleteMessage); } else { Console.WriteLine("Sorry. You cannot read from this NetworkStream."); } 

试试这段代码:

 using (NetworkStream stream = client.GetStream()) { do { Thread.Sleep(20); } while (!stream.DataAvailable); if (stream.DataAvailable && stream.CanRead) { Byte[] data = new Byte[1024]; List allData = new List(); do { int numBytesRead = stream.Read(data,0,data.Length); if (numBytesRead == data.Length) { allData.AddRange(data); } else if (numBytesRead > 0) { allData.AddRange(data.Take(bytes)); } } while (stream.DataAvailable); } } 

希望这会有所帮助,它应该可以防止您错过任何发送给您的数据。

试试这个:

  private string GetResponse(NetworkStream stream) { byte[] data = new byte[1024]; using (MemoryStream memoryStream = new MemoryStream()) { do { stream.Read(data, 0, data.Length); memoryStream.Write(data, 0, data.Length); } while (stream.DataAvailable); return Encoding.ASCII.GetString(memoryStream.ToArray(), 0, (int)memoryStream.Length); } } 

TCP本身没有任何方法来定义“数据结束”条件。 这是应用程序级别协议的责任。

例如,请参阅HTTP请求描述:

客户端请求(包括请求行的这种情况,只有一个头字段)后跟一个空行,以便请求以双换行结束

因此,对于请求,数据结束由两个换行序列确定。 并作出回应:

Content-Type指定HTTP消息传送的数据的Internet媒体类型,而Content-Length指示其长度(以字节为单位)。

响应内容大小在数据前的标头中指定。 因此,您可以自行决定如何对一次传输的数据进行编码 – 它可以只是数据开头的前2或4个字节,只需要读取总大小或更复杂的方式。

对于我的场景,消息本身告诉后续消息的长度。 这是代码

  int lengthOfMessage=1024; string message = ""; using (MemoryStream ms = new MemoryStream()) { int numBytesRead; while ((numBytesRead = memStream.Read(MessageBytes, 0, lengthOfMessage)) > 0) { lengthOfMessage = lengthOfMessage - numBytesRead; ms.Write(MessageBytes, 0, numBytesRead); } message = Encoding.ASCII.GetString(ms.ToArray(), 0, (int)ms.Length); } 

加入这个问题有点晚了,但我只是想知道自己最好的办法是什么。 当协议未知时……这是我的结论

之前的答案中提到的while循环在NetworkStream上无法正常工作,它们会失败并且您根本没有数据。

我没有尝试过DataAvailable,也不知道它是如何工作的我更喜欢我的版本,任何人都可以理解。

 var ms = new MemoryStream(); byte[] data = new byte[1024]; int numBytesRead; do { numBytesRead = stream.Read(data, 0, data.Length); ms.Write(data, 0, numBytesRead); } while (numBytesRead == data.Length); var str = Encoding.ASCII.GetString(ms.ToArray());