【发布时间】:2016-09-13 14:33:40
【问题描述】:
我使用 TcpClient 和 TcpListener 类在两个应用程序之间交换一些对象。我使用 XML 序列化(见下面的代码)。基本上一切正常。问题是当一个应用程序在短时间内发送多个对象时,我在接收端的 MemoryStream 中有多个对象(多个根元素,也带有 XML 版本标记)。我如何处理所有对象,最好的方法是什么?我可以将对象分组到一个列表中并对整个列表进行反序列化,但迟早我会面临同样的问题。 我认为这似乎是一个常见问题,但我还没有找到解决方案。
要序列化的对象:
public class DataModel
{
public string Command { get; set; }
public string Value { get; set; }
// ctor etc
}
接收方:
private void onRead(IAsyncResult ar)
{
int nBytes = _client.GetStream().EndRead(ar);
XmlSerializer serializer = new XmlSerializer(typeof(DataModel));
MemoryStream memStream = new MemoryStream(buffer);
DataModel dmo = (DataModel)serializer.Deserialize(memStream);
buffer = new byte[1024];
_client.GetStream().BeginRead(buffer, 0, buffer.Length, new AsyncCallback(onRead), null);
// read on if more available...
}
流内容示例:
<?xml version="1.0"?>
<DataModel xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<Command>XXX</Command>
<Value>1.0</Value>
</DataModel><?xml version="1.0"?>
<DataModel xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<Command>XXX</Command>
<Value>5</Value>
</DataModel><?xml version="1.0"?>
<DataModel xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<Command>XXX</Command>
<Value>YYY</Value>
</DataModel>
我删除了 try/catch、调试和所有不必要的东西
【问题讨论】:
-
无论何时发送数据,您都需要使用以下一种或多种技术终止每条消息 1) ASCII:使用消息中未使用的已知字符终止每条消息 2) ASCII 或二进制:添加前缀带有字节数的消息。 3) Ascii 或 Binary:发送固定长度的消息。在您的情况下,我将使用 ETX (0x03) 或 EOT (0x04) 之类的字符终止每个 DataModel 元素。然后在保存 xml 之前删除字符。分别处理每个元素。
标签: c# xml serialization tcp memorystream