gpt4 book ai didi

serialization - protobuf-net是否比二进制序列化还快?

转载 作者:行者123 更新时间:2023-12-04 04:45:58 28 4
gpt4 key购买 nike

我编写了一个程序,使用XMLSerializer,BinaryFormatter和ProtoBuf序列化“Person”类。我认为protobuf-net应该比其他两个要快。 Protobuf序列化比XMLSerialization快,但比二进制序列化慢得多。我的理解不正确吗?请让我明白这一点。感谢您的帮助。

编辑:-我更改了代码(在下面更新),以仅测量序列化的时间,而不创建流,并且仍然看到差异。可以告诉我为什么吗?

以下是的输出:-

在347毫秒内使用 Protocol Buffer 创建了人员

在1462毫秒内使用XML创建了人

在2毫秒内使用二进制创建了人员

下面的代码

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using ProtoBuf;
using System.IO;
using System.Diagnostics;
using System.Runtime.Serialization.Formatters.Binary;
namespace ProtocolBuffers
{
class Program
{
static void Main(string[] args)
{

string folderPath = @"E:\Ashish\Research\VS Solutions\ProtocolBuffers\ProtocolBuffer1\bin\Debug";
string XMLSerializedFileName = Path.Combine(folderPath,"PersonXMLSerialized.xml");
string ProtocolBufferFileName = Path.Combine(folderPath,"PersonProtocalBuffer.bin");
string BinarySerializedFileName = Path.Combine(folderPath,"PersonBinary.bin");

if (File.Exists(XMLSerializedFileName))
{
File.Delete(XMLSerializedFileName);
Console.WriteLine(XMLSerializedFileName + " deleted");
}
if (File.Exists(ProtocolBufferFileName))
{
File.Delete(ProtocolBufferFileName);
Console.WriteLine(ProtocolBufferFileName + " deleted");
}
if (File.Exists(BinarySerializedFileName))
{
File.Delete(BinarySerializedFileName);
Console.WriteLine(BinarySerializedFileName + " deleted");
}

var person = new Person
{
Id = 12345,
Name = "Fred",
Address = new Address
{
Line1 = "Flat 1",
Line2 = "The Meadows"
}
};

Stopwatch watch = Stopwatch.StartNew();

using (var file = File.Create(ProtocolBufferFileName))
{
watch.Start();
Serializer.Serialize(file, person);
watch.Stop();
}

//Console.WriteLine(watch.ElapsedMilliseconds.ToString());
Console.WriteLine("Person got created using protocol buffer in " + watch.ElapsedMilliseconds.ToString() + " milliseconds ");

watch.Reset();

System.Xml.Serialization.XmlSerializer x = new System.Xml.Serialization.XmlSerializer(person.GetType());
using (TextWriter w = new StreamWriter(XMLSerializedFileName))
{
watch.Start();
x.Serialize(w, person);
watch.Stop();
}

//Console.WriteLine(watch.ElapsedMilliseconds.ToString());
Console.WriteLine("Person got created using XML in " + watch.ElapsedMilliseconds.ToString() + " milliseconds");

watch.Reset();

using (Stream stream = File.Open(BinarySerializedFileName, FileMode.Create))
{
BinaryFormatter bformatter = new BinaryFormatter();
//Console.WriteLine("Writing Employee Information");
watch.Start();
bformatter.Serialize(stream, person);
watch.Stop();
}

//Console.WriteLine(watch.ElapsedMilliseconds.ToString());
Console.WriteLine("Person got created using binary in " + watch.ElapsedMilliseconds.ToString() + " milliseconds");

Console.ReadLine();



}
}


[ProtoContract]
[Serializable]
public class Person
{
[ProtoMember(1)]
public int Id { get; set; }
[ProtoMember(2)]
public string Name { get; set; }
[ProtoMember(3)]
public Address Address { get; set; }
}
[ProtoContract]
[Serializable]
public class Address
{
[ProtoMember(1)]
public string Line1 { get; set; }
[ProtoMember(2)]
public string Line2 { get; set; }
}
}

最佳答案

我回复了您的电子邮件;我不知道您也将其张贴在这里。我的第一个问题是:protobuf-net的哪个版本?我问的原因是“v2”的开发干线故意禁用了自动编译功能,因此我可以使用单元测试来测试运行时版本和预编译版本。因此,如果您使用的是“v2”(仅在源代码中可用),则需要告诉它编译模型-否则它将运行100%反射。

在“v1”或“v2”中,您可以使用以下方法执行此操作:

Serializer.PrepareSerializer<Person>();

完成此操作后,我得到的数字(从您电子邮件中的代码;我没有检查上面的代码是否是相同的示例):
10
Person got created using protocol buffer in 10 milliseconds
197
Person got created using XML in 197 milliseconds
3
Person got created using binary in 3 milliseconds

另一个因素是重复。坦率地说3到10毫秒什么都没有;您无法比较此级别附近的数字。将其重复执行5000次(重新使用 XmlSerializer/ BinaryFormatter实例;没有引入虚假成本),我得到:
110
Person got created using protocol buffer in 110 milliseconds
329
Person got created using XML in 329 milliseconds
133
Person got created using binary in 133 milliseconds

将其带到更极端的极端(100000):
1544
Person got created using protocol buffer in 1544 milliseconds
3009
Person got created using XML in 3009 milliseconds
3087
Person got created using binary in 3087 milliseconds

因此最终:
  • 当您几乎没有可序列化的数据时,大多数方法将非常快(包括protobuf-net)
  • 在添加数据时,差异变得更加明显; protobuf通常在这里比较擅长,对于单个大图或许多小图

  • 还要注意,在“v2”中,编译后的模型可以完全静态编译(到可以部署的dll中),甚至省去了(已经很小的)启动成本。

    关于serialization - protobuf-net是否比二进制序列化还快?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2966500/

    28 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com