Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/311.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 用于简单数据结构的最轻序列化方法_C#_Xml_Json_Serialization_Xml Serialization - Fatal编程技术网

C# 用于简单数据结构的最轻序列化方法

C# 用于简单数据结构的最轻序列化方法,c#,xml,json,serialization,xml-serialization,C#,Xml,Json,Serialization,Xml Serialization,我有一个简单的数据结构,我想在不增加太多开销的情况下序列化它。 在数据大小方面,你认为哪种方法最好? 数据中不存在使用分隔符作为“#”或其他字符(我是100%)的自定义序列化/反序列化 XML序列化 JSON 其他 我使用带有#作为分隔符的自定义序列化,因为我100%确定我的数据中没有该字符 数据结构示例: string Title int ChapterIndex List<String> Paragraphs XML: [

我有一个简单的数据结构,我想在不增加太多开销的情况下序列化它。 在数据大小方面,你认为哪种方法最好?

  • 数据中不存在使用分隔符作为“#”或其他字符(我是100%)的自定义序列化/反序列化
  • XML序列化
  • JSON
  • 其他
我使用带有#作为分隔符的自定义序列化,因为我100%确定我的数据中没有该字符

数据结构示例:

string        Title       
int           ChapterIndex
List<String>  Paragraphs
XML:

[
 {
    "title": "some title 0",
    "chapterIndex": 0,
    "paragraphs": ["p1", "p2", "p3", "p4"]
 },
 {
    "title": "some title 1",
    "chapterIndex": 1,
    "paragraphs": ["p1chap1", "p2chap1", "p3chap1", "p4chap1"]
 }
]
<RootTag>
    <item title="some title 0" chapterIndex="0">
        <paragraph>p1</paragraph>
        <paragraph>p2</paragraph>
        <paragraph>p3</paragraph>
        <paragraph>p4</paragraph>
    </item>
    <item title="some title 1" chapterIndex="1">
        <paragraph>p1chap1</paragraph>
        <paragraph>p2chap1</paragraph>
        <paragraph>p3chap1</paragraph>
        <paragraph>p4chap1</paragraph>
    </item>
</RootTag>
[{"title":"some title 0","chapterIndex":0,"paragraphs":["p1","p2","p3","p4"]},{"title":"some title 1","chapterIndex":1,"paragraphs":["p1chap1","p2chap1","p3chap1","p4chap1"]}]
<RootTag><item title="some title 0" chapterIndex="0"><paragraph>p1</paragraph><paragraph>p2</paragraph><paragraph>p3</paragraph><paragraph>p4</paragraph></item><item title="some title 1" chapterIndex="1"><paragraph>p1chap1</paragraph><paragraph>p2chap1</paragraph><paragraph>p3chap1</paragraph><paragraph>p4chap1</paragraph></item></RootTag>
some title 0##0##p1#p2#p3#p4###some title 1##1##p1chap1#p2chap1#p3chap1#p4chap1###and_so_on
XML:

[
 {
    "title": "some title 0",
    "chapterIndex": 0,
    "paragraphs": ["p1", "p2", "p3", "p4"]
 },
 {
    "title": "some title 1",
    "chapterIndex": 1,
    "paragraphs": ["p1chap1", "p2chap1", "p3chap1", "p4chap1"]
 }
]
<RootTag>
    <item title="some title 0" chapterIndex="0">
        <paragraph>p1</paragraph>
        <paragraph>p2</paragraph>
        <paragraph>p3</paragraph>
        <paragraph>p4</paragraph>
    </item>
    <item title="some title 1" chapterIndex="1">
        <paragraph>p1chap1</paragraph>
        <paragraph>p2chap1</paragraph>
        <paragraph>p3chap1</paragraph>
        <paragraph>p4chap1</paragraph>
    </item>
</RootTag>
[{"title":"some title 0","chapterIndex":0,"paragraphs":["p1","p2","p3","p4"]},{"title":"some title 1","chapterIndex":1,"paragraphs":["p1chap1","p2chap1","p3chap1","p4chap1"]}]
<RootTag><item title="some title 0" chapterIndex="0"><paragraph>p1</paragraph><paragraph>p2</paragraph><paragraph>p3</paragraph><paragraph>p4</paragraph></item><item title="some title 1" chapterIndex="1"><paragraph>p1chap1</paragraph><paragraph>p2chap1</paragraph><paragraph>p3chap1</paragraph><paragraph>p4chap1</paragraph></item></RootTag>
some title 0##0##p1#p2#p3#p4###some title 1##1##p1chap1#p2chap1#p3chap1#p4chap1###and_so_on
自定义优化:

some title 0§0§p1#p2#p3#p4¤some title 1§1§p1chap1#p2chap1#p3chap1#p4chap1¤and_so_on
拥有

  • ·作为列表项分隔符
  • §作为项目分隔符内的属性
  • #作为段落内容分隔符
更新:
在我的例子中,字符串多于整数,因为它是一种图书/歌词应用程序,只需要标题chapternumber/lyricId和歌词的所有段落。

在我看来,JSON是最简单的方法,也不会产生任何开销。 这里:您可以看到JSON和XML之间的区别


JSON解析器将自动为您完成所有工作。

我在项目中一直使用谷歌的序列化,这是迄今为止最轻的序列化之一。

决定起来很复杂。如果您的类主要由字符串组成,那么您的方法会更好。唯一“更好”的方法是压缩结果流(创建序列化数据后仍然可以这样做)

如果您的数据主要是数字/非字符串,那么/是二进制序列化程序,它们的输出应该小于序列化程序,因为您使用5个字节来序列化
10000
,而二进制序列化程序可能只使用2-4个字节

Json和xml序列化程序肯定会生成更大的序列化数据,因为它们都是“文本的”(因此它们将数字
10000
序列化为
10000
)(序列化程序也是如此),并且它们还包括附加的标记,这些标记是非空的,根据定义不小于单个字符

现在。。。编写自定义序列化程序还是使用?我会说,我更信任Marc Gravell(protobuf)编写的基于谷歌创建的“标准”的序列化程序,而不是我编写的序列化程序:-),因为现在您正在序列化整数和字符串。。。但也许明天您需要序列化
DateTime
float
或其他复杂类型。是否比正确实现序列化所需的小时数少100字节?必须由你来决定

Protobuf的一个示例:

[ProtoContract]
public class MyObject
{
    [ProtoMember(1)]
    public string title { get; set; }
    [ProtoMember(2)]
    public int chapterIndex { get; set; }
    [ProtoMember(3)]
    public List<String> paragraphs { get; set; }
}

var myo = new[] 
{ 
    new MyObject
    {
        title = "some title 0",
        chapterIndex = 0,
        paragraphs = new List<string> { "p1", "p2", "p3", "p4" }
    }, 
    new MyObject
    {
        title = "some title 1",
        chapterIndex = 1,
        paragraphs = new List<string> { "p1chap1", "p2chap1", "p3chap1", "p4chap1" }
    }, 
};

byte[] bytes;

using (var ms = new MemoryStream())
{
    Serializer.Serialize(ms, myo);
    bytes = ms.ToArray();
}

using (var ms = new MemoryStream(bytes))
{
    MyObject[] myo2 = Serializer.Deserialize<MyObject[]>(ms);
}
[协议]
公共类MyObject
{
[原成员(1)]
公共字符串标题{get;set;}
[原成员(2)]
公共int chapterIndex{get;set;}
[原成员(3)]
公共列表段落{get;set;}
}
var myo=new[]
{ 
新对象
{
title=“某些标题0”,
chapterIndex=0,
段落=新列表{“p1”、“p2”、“p3”、“p4”}
}, 
新对象
{
title=“某些标题1”,
chapterIndex=1,
段落=新列表{“p1chap1”、“p2chap1”、“p3chap1”、“p4chap1”}
}, 
};
字节[]字节;
使用(var ms=new MemoryStream())
{
Serializer.Serialize(ms,myo);
字节=ms.ToArray();
}
使用(var ms=新内存流(字节))
{
MyObject[]myo2=序列化程序。反序列化(ms);
}

字节[]
的长度为86,因此只比自定义格式设置程序(81)长一点。但请注意,这是一个单数字字段,您使用的是单位数。关键是,
protobuf
可能更好,因为它是由专业人士编写的,并且没有序列化程序的限制。

在尝试了答案中提供的所有序列化类型后,我找到了问题的答案

当且仅当满足以下要求时

  • 数据大小优先级
  • 简单的数据结构
  • 需要自定义序列化和反序列化
  • 了解数据内容以正确选择分隔符
只有在这些条件下,才能使用自定义序列化,如我的问题所示

关于性能?

这完全取决于您如何编写反序列化方法。

我不确定是否没有开销总是有开销/额外数据来分隔项我认为这不是开销。对我来说,开销是XML所做的。编辑:但我认为你的方法要短得多,而且看起来相当不错。你是对的,我误解了“开销”这个词,将其解释为“额外/附件”没问题。嗯,我想你回答了你自己的问题。你应该使用你的方法。关于这个话题,你还有其他问题吗?我在等待回答proto-buf的人提供一个例子,看看这是否比custom更好/更轻example@csharpwinphonexaml好啊你是对的:-)所以我更新了答案。谢谢你更新了答案,考虑到我的数据主要是字符串,有没有一种混合方法可以将数字序列化为字符,以避免使用4个字节作为2个字节的数字?你能提供基于我的数据的protobuf中序列化结果的示例吗?@csharpwinphonexaml完成了第二部分。对于第一部分,我不会帮你浪费时间来节省一些时间。我认为这是一个非常合理的结论。恭喜你能认真思考你的问题。