c# - 将 Newtonsoft JSON 序列化为字节数组

标签 c# json.net

我的目标是发送包含 header 对象的 JSON 和字节数组字段中的压缩数据。

[JsonObject(MemberSerialization.OptOut)]
public class Message
{
    public Message()
    {
        Header = new Header();
    }

    public Header Header { get; set; }


    public byte[] Data { get; set; }
}

字节数组是 gzip 压缩的 JSON 对象,但这不是那么相关。我遇到的问题是,如果我序列化 JSON,它会转换为字符串,然后再转换回字节。问题是,消息大小增加了很多,因为序列化字节数组会将其转换为字符串表示形式。

我受到最大消息大小的限制,并且我有适当的压缩数据,但是当我发送包含字节数组和未压缩 header 中的压缩数据的 JSON 时,序列化 JSON 对象使我超出了消息大小限制。

有什么可靠的方法可以直接将 JSON 对象转换为字节数组。

var stringMessage = JsonConvert.SerializeObject(message,Formatting.None);
var bytes = Encoding.UTF8.GetBytes(stringMessage);

var stringMessage2 = JsonConvert.SerializeObject(message.TransportHeader, Formatting.None);
var bytes2 = Encoding.UTF8.GetBytes(stringMessage2);

Message eventMessage = new Message(bytes);
var bytes3= Encoding.UTF8.GetBytes(JsonConvert.SerializeObject(message.Transportdata));

压缩数据大小=243905

序列化后以字节为单位的完整 JSON = 325313

仅 header 字节大小=90

只是将压缩数据序列化并转换回字节 = 325210,(当数据被 JsonConvert.SerializeObject 序列化并生成字符串表示时,大小会增加)

它显然上升了很多,这是由字节数组引起的。

最佳答案

我找到了一种方法来做我想做的事,它不完全是 JSON,而是 BSON 或也称为二进制 JSON。既然找到解决方案纯属运气,我不确定 BSON 的知名度如何。

无论如何,Newtonsoft 通过位于 https://www.nuget.org/packages/Newtonsoft.Json.Bson/1.0.1 的 Newtonsoft.Json.Bson nuget 包支持它

一些序列化/反序列化的代码

foreach (var message in transportMessageList)
{
    MemoryStream ms = new MemoryStream();
    using (BsonDataWriter writer = new BsonDataWriter(ms))
    {
        JsonSerializer serializer = new JsonSerializer();
        serializer.Serialize(writer, message);
    }

    var bsonByteArray = ms.ToArray();
    Assert.True(bsonByteArray.Length!=0);
    bsonList.Add(bsonByteArray);
}

var deserializdTransmortMessageList = new List<TransportMessage>();
foreach (var byteArray in bsonList)
{
    TransportMessage message;
    MemoryStream ms = new MemoryStream(byteArray);
    using (BsonDataReader reader = new BsonDataReader(ms))
    {
        JsonSerializer serializer = new JsonSerializer();
        message = serializer.Deserialize<TransportMessage>(reader);
    }
    Assert.True(message.Transportdata.Length!=0);
    deserializdTransmortMessageList.Add(message);
}

您可以使用与 JSON 相同的类/对象,序列化压缩的字节数组不再导致大小增加。

请注意,Newtonsoft 网站上的 BSON 文档已过时,目前仅列出已弃用的 API 调用。我的代码使用适当的未弃用的 API 调用。

关于c# - 将 Newtonsoft JSON 序列化为字节数组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52650402/

相关文章:

c# - 如何告诉 Json.NET 忽略第 3 方对象中的属性?

json - 如何反序列化可以是数组或单个对象的 JSON

c# - Newtonsoft DeserializeXNode 错误地扩展了内部数组

c# - JsonPropertyAttribute 中的 JSON.NET NullValueHandling 未按预期工作

c# - 为什么我不能使用 Json.Net 反序列化这个自定义结构?

c# - 使用 Json.NET 将 JSON 反序列化为对象

c# - 如何开始开发 Internet Explorer 扩展?

c# - VSTO WPF 模式对话框光标在文本框中不闪烁

c# - 与在 C# 中声明新变量相比,使用条件运算符为列表字段赋值是最好的方法吗?

c# - 使用 Table-Per-Hierarchy 继承模型访问相关实体的影子属性