将对象序列化为最小的UTF8兼容大小

时间:2011-04-27 09:23:47

标签: c# serialization utf-8

我有一个非常简单的类,它包含一些原始类型和一些主要包含枚举的集合。现在我需要将此对象序列化为UTF8兼容的最小可能大小。

这是我需要序列化的类

public class Context
{
    public Hashtable UserModuleRoles { get; set; }
    public Dictionary<string, object> CustomSettings { get; set; }
    public int Uid { get; set; }
    public int Id { get; set; }
    public int ActiveId { get; set; }
    public byte Default { get; set; }
    public SetEnum Ident { get; set; }
    public string Name { get; set; }
    public sbyte State { get; set; }
    public DateTime Date { get; set; }
}

这是我序列化对象的方法

public string Serialize(object serializeObject)
{
    MemoryStream stream = new MemoryStream();
    BinaryFormatter b = new BinaryFormatter();

    b.Serialize(stream, serializeObject);

    byte[] data = stream.ToArray();

    stream.Dispose();
    stream = new MemoryStream();

    using (ZipFile zip = new ZipFile())
    {
        zip.AddEntry("data", data);
        zip.Save(stream);
    }

    data = stream.ToArray();
    stream.Dispose();

    return Convert.ToBase64String(data);
}

在我的第一次尝试中,我序列化对象,压缩该内容(约1/3小)并将其转换为base64字符串。但是base64的开销很大,只有1/3,我知道有base128,但我不知道如何开始,我对base128编码的搜索不成功。

  • 或者还有其他方法吗?

  • 如果不是,最好的方法是什么? 这是base128?

编辑:

我使用整个“Context”对象测试了ObjectStateFormatter类,这导致8byte更多和更慢的序列化/反序列化。也许我只能在属性而不是全班使用它?

2 个答案:

答案 0 :(得分:2)

嗯,如果你知道base64是如何完成的,那么base128就不那么难了。荷兰维基百科很好地描述了这个过程(为你翻译):

  1. 将数据转换为二进制。
  2. 继续采用7位(2 ^ 7 = 128)
  3. 的块
  4. 将这7位转换为整数。
  5. 在您定义的转换表中查找该整数,并将找到的字符附加到base128字符串。
  6. 该转换表包含128个兼容的UTF8字符,例如:

    0: a
    1: b
    ..
    25: z
    26: 0
    

    唯一的要求是发送方和接收方的转换表都是相同的。

答案 1 :(得分:0)

尝试使用objectstateformatter代替BinaryFormatter,可能会缩小尺寸。这完全取决于您序列化的数据。