protobuf-net是否有任何API将protobuf转换为人类可读的形式?我希望像TextFormat这样的东西.
在Unity 3D中,有一个带有Transform属性的GameObject.变换具有位置(Vector3)和旋转(四元数).我想通过protobuf-net将这些GameObjects发送到后备存储中.我目前正在使用以下代码,但GameObject.transform.position.x,y,z和transform.rotation.x,y,z,w似乎没有存储在序列化文件中?
RuntimeTypeModel model = TypeModel.Create();
model.AutoAddMissingTypes = true;
model.Add(typeof(Vector3), true).Add("x","y","z");
model.Add(typeof(Transform), true).Add("position").Add("rotation");
model.Add(typeof(Quaternion), true).Add("x","y","z","w");
model.Add(typeof(GameObject), true).Add("transform").Add("name");
model.SerializeWithLengthPrefix(fs, go, typeof(GameObject), PrefixStyle.Base128, 0);
Run Code Online (Sandbox Code Playgroud)
反序列化:
using (FileStream fs = new FileStream(path, FileMode.Open))
{
fs.Position = 0;
RuntimeTypeModel model = TypeModel.Create();
model.AutoAddMissingTypes = true;
model.Add(typeof(Vector3), true).Add("x","y","z");
model.Add(typeof(Transform), true).Add("position").Add("rotation"); ;
model.Add(typeof(Quaternion), true).Add("x","y","z","w");
model.Add(typeof(GameObject), true).Add("transform").Add("name");
do
{
len = ProtoReader.ReadLengthPrefix(fs, false, PrefixStyle.Base128, out fieldNumber, out bytesRead);
if (bytesRead <= 0) continue;
gos.Add((GameObject)model.Deserialize(fs, null, typeof(GameObject), len));
} while (bytesRead > 0);
}
Run Code Online (Sandbox Code Playgroud)
我似乎回到了正确数量的GameObjects,但反序列化唯一正确的是.name属性.我没有使用当前代码转换Transform类的子属性.任何想法都会非常有用!
谢谢-
根据我的评论,这里是堆栈跟踪: …
Heyup.protobuf.net的长期爱好者.
但是问题很快.我有一个高度多线程的C#应用程序,可以反序列化大约100个对象/秒,大约50MB /秒.我看到非常大的内存使用量,远远超过我正在反序列化的内存.我通过'Red Gate ANTS Memory Profiler'运行应用程序,由于protobuf(超过50%的应用程序使用),它向我展示了大量的第2代内存对象.大多数对象都是int值,并与以下内容链接:
- TypeModel.TryDeserializeList()
- ProtoBuf.Meta.BasicList
Run Code Online (Sandbox Code Playgroud)
任何帮助减少这个第2代内存使用将是值得赞赏的.
渣
我正在尝试通过protobuf-net发送IPEndpoint,我观察到的是当将4字节数组反序列化为IP4地址时,设置代码接收8字节的值.包含orignal地址的四个字节,以及包含已序列化地址的另外4个字节.通过逐步执行代码,我已经能够确认在调用Deserialize时,它首先读取字节,然后设置它们的字节.
在做了一些阅读后,我了解了OverwriteList,并且如下例所示,我已将其设置为true.但是,设置器仍然提供8字节值.
有谁知道我做错了什么?
当与protobuf-net r480,Visual Studio 2010一起用作.Net 4.0控制台应用程序时,此示例代码应抛出异常.
using ProtoBuf;
using System.Net;
using System.IO;
namespace ConsoleApplication1
{
[ProtoContract]
class AddressOWner
{
private IPEndPoint endpoint;
public AddressOWner()
{ endpoint = new IPEndPoint(new IPAddress(new byte[] {8,8,8,8}), 0); }
public AddressOWner(IPEndPoint newendpoint)
{ this.endpoint = newendpoint; }
[ProtoMember(1, OverwriteList=true)]
public byte[] AddressBytes
{
get { return endpoint.Address.GetAddressBytes(); }
set { endpoint.Address = new IPAddress(value); }
}
}
class Program
{
static void Main(string[] args)
{
AddressOWner ao = new AddressOWner(new IPEndPoint(new IPAddress(new byte[] … 我正在尝试编写一些代码,这些代码将从protobuf-net(V2)运行时类型模型中生成准确的.proto文件,因此我可以编写一个能够反序列化protobuf-net生成的消息的python客户端.
我有点卡在日期时间的消息应该是什么样的,有人可以对此有所了解吗?
谢谢<3
是否可以转储(查看)以PB格式写入的数据,而无需了解用于写入该数据的类型?
简而言之,在线上,protobufs被编码为3元组,其中键是分配给.proto模式中的字段的字段编号.类型是其中之一.它包含足够的信息来解码3元组的值,即它告诉你值的长度.
我的最终目标是为Fiddler2编写扩展,以查看以PB格式发送/接收的内容.
快速问题,默认情况下是否可以在所有枚举类型上启用EnumPassthru?目前我必须手动在每个枚举类型上启用它,或使用以下方法将其自动应用于我的DTO程序集类型:
public static void ConfigureEnumTypes(RuntimeTypeModel tm, Assembly a)
{
foreach (var type in a.GetTypes())
{
if (type.IsEnum && type.GetCustomAttribute<ProtoContractAttribute>() != null)
tm[type].EnumPassthru = true;
}
}
Run Code Online (Sandbox Code Playgroud)
如果有更好的方法,我想知道.谢谢.
我正在使用一个包含超过五百万个项目的列表和词典的系统,其中每个项目通常是一个具有多达90个原始属性的平面dto.使用protobuf-net将集合持久保存到磁盘,以实现弹性和子序列处理.
不出所料,我们在处理和序列化过程中遇到了LOH.
我们可以在处理过程中使用ConcurrentBag等来避免LOH,但是在序列化时我们仍遇到问题.
目前,集合中的项目被批量分组为1000个并且并行地序列化为内存流.每个字节数组都放在一个并发队列中,以便稍后写入文件流.
虽然我明白这是在尝试做什么,但它似乎过于复杂.感觉就像protobuf本身应该有一些东西可以在不使用LOH的情况下处理大量的收藏.
我希望我犯了一个小学生错误 - 我忽略了一些设置.否则,我将寻求编写自定义二进制读取器/写入器.
我应该指出我们正在使用4.0,希望尽快转向4.5但是我们意识到尽管GC有所改进,我们仍然无法解决这个问题.
任何帮助赞赏.
我现在用谷歌搜索了一下,但是无法确定protobuf-net或protobuf是否通常支持以下意义上的向前兼容性:
该对象的旧版本使用新字段反序列化该对象的新版本,但在将其序列化时保留该字段,因此该对象的新版本不会丢失该值.
这与protobuf有关吗?
非常感谢
有没有办法让protobuf序列化/反序列化F#的歧视联盟?
我正在尝试使用protobuf序列化消息.消息是F#记录和受歧视的联合.
序列化似乎适用于记录,但我不能让它与歧视的联合工作.
在下面的代码中,测试testMessageA和testMessageB是绿色的.测试testMessageDU为红色.
module ProtoBufSerialization
open FsUnit
open NUnit.Framework
open ProtoBuf
type MessageA = {
X: string;
Y: int;
}
type MessageB = {
A: string;
B: string;
}
type Message =
| MessageA of MessageA
| MessageB of MessageB
let serialize msg =
use ms = new System.IO.MemoryStream()
Serializer.SerializeWithLengthPrefix(ms, msg, PrefixStyle.Fixed32)
ms.ToArray()
let deserialize<'TMessage> bytes =
use ms = new System.IO.MemoryStream(buffer=bytes)
Serializer.DeserializeWithLengthPrefix<'TMessage>(ms, PrefixStyle.Fixed32)
[<Test>]
let testMessageA() =
let msg = {X="foo"; Y=32}
msg |> serialize |> deserialize<MessageA> |> …Run Code Online (Sandbox Code Playgroud)