Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/301.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# 如何序列化/反序列化列表<;类对象>;用protobuf?_C#_Serialization_Protocol Buffers_Protobuf Net - Fatal编程技术网

C# 如何序列化/反序列化列表<;类对象>;用protobuf?

C# 如何序列化/反序列化列表<;类对象>;用protobuf?,c#,serialization,protocol-buffers,protobuf-net,C#,Serialization,Protocol Buffers,Protobuf Net,我想序列化列表 我读过这篇文章,但仍然找不到解决办法。如何对其进行序列化和反序列化 我的类和结构: [Serializable, ProtoContract(Name = @"Archive"), ProtoInclude(1, typeof(List<ArchiveData>))] public partial class Archive : IExtensible { [ProtoMember(1, IsRequired = true, OverwriteList = t

我想序列化
列表

我读过这篇文章,但仍然找不到解决办法。如何对其进行序列化和反序列化

我的类和结构:

[Serializable, ProtoContract(Name = @"Archive"), ProtoInclude(1, typeof(List<ArchiveData>))]
public partial class Archive : IExtensible
{
    [ProtoMember(1, IsRequired = true, OverwriteList = true, Name = @"data", DataFormat = DataFormat.Default)]
    public List<ArchiveData> data { get; set; }

    public Archive()
    {
        data = new List<ArchiveForm.ArchiveData>();
    }

    private IExtension extensionObject;
    IExtension IExtensible.GetExtensionObject(bool createIfMissing)
    {
        return Extensible.GetExtensionObject(ref extensionObject, createIfMissing);
    }
}

public struct ArchiveData
{
    [ProtoMember(1, IsRequired = false, OverwriteList = true, Name = @"sourcefolder", DataFormat = DataFormat.Default)]
    [global::System.ComponentModel.DefaultValue("")]
    public string sourcefolder { get; set; }

    [ProtoMember(2, IsRequired = false, OverwriteList = true, Name = @"destinationfolder", DataFormat = DataFormat.Default)]
    [global::System.ComponentModel.DefaultValue("")]
    public string destinationfolder { get; set; }

    [ProtoMember(3, IsRequired = false, OverwriteList = true, Name = @"period", DataFormat = DataFormat.FixedSize)]
    [global::System.ComponentModel.DefaultValue((int)0)]
    public int period { get; set; }

    public ArchiveData(string sfolder = "", string dfolder = "", int priod = 0)
    {
        sourcefolder = sfolder;
        destinationfolder = dfolder;
        period = priod;
    }
}
------------------------------编辑------------------------------

已添加此部分以获取更多信息。当我像下面的代码一样使用SerializeWithLengthPrefix/DeserializeWithLengthPrefix函数时,对于我使用反序列化函数的第一个类,它每次都能正常工作。但是对于我使用反序列化函数的第二个类,它返回null

[Serializable, ProtoContract(Name = @"OptionData")]
public class OptionData : IExtensible
{
    [ProtoMember(1, IsRequired = false, OverwriteList = true, Name = @"StartWithWindows", DataFormat = DataFormat.Default)]
    [DefaultValue(false)]
    public bool StartWithWindows { get; set; }

    [ProtoMember(2, IsRequired = false, OverwriteList = true, Name = @"AutoBackup", DataFormat = DataFormat.Default)]
    [DefaultValue(false)]
    public bool AutoBackup { get; set; }

    [ProtoMember(3, IsRequired = false, OverwriteList = true, Name = @"Speed", DataFormat = DataFormat.FixedSize)]
    [DefaultValue((int)0)]
    public int Speed { get; set; }

    private IExtension extensionObject;
    IExtension IExtensible.GetExtensionObject(bool createIfMissing)
    {
        return Extensible.GetExtensionObject(ref extensionObject, createIfMissing);
    }
}

public static void Update(OptionData op)
{
    using (var fs = File.Create(probuffile))
    {
        Serializer.SerializeWithLengthPrefix(fs, op, PrefixStyle.Base128, 3);
    }
}

public static void Update(Archive arc)
{
    using (var fs = File.Create(probuffile))
    {
        Serializer.SerializeWithLengthPrefix<Archive>(fs, arc, PrefixStyle.Base128, 2);
    }
}

public static void Refresh(ref OptionData op)
{
    if (File.Exists(probuffile))
    {
        using (var fs = File.OpenRead(probuffile))
        {
            op = Serializer.DeserializeWithLengthPrefix<OptionData>(fs, PrefixStyle.Base128, 3);
        }
    }
}

public static void Refresh(ref Archive arc)
{
    if (File.Exists(probuffile))
    {
        using (var fs = File.OpenRead(probuffile))
        {
            arc = Serializer.DeserializeWithLengthPrefix<Archive>(fs, PrefixStyle.Base128, 2);
        }
    }
}
[可序列化,协议(名称=@“OptionData”)]
公共类选项数据:可扩展
{
[ProtoMember(1,IsRequired=false,OverwriteList=true,Name=@“StartWithWindows”,DataFormat=DataFormat.Default)]
[默认值(false)]
公共bool StartWithWindows{get;set;}
[ProtoMember(2,IsRequired=false,OverwriteList=true,Name=@“AutoBackup”,DataFormat=DataFormat.Default)]
[默认值(false)]
公共布尔自动备份{get;set;}
[ProtoMember(3,IsRequired=false,OverwriteList=true,Name=@“Speed”,DataFormat=DataFormat.FixedSize)]
[默认值((int)0)]
公共整数速度{get;set;}
私有IExtension扩展对象;
IExtension IExtensible.GetExtensionObject(bool createIfMissing)
{
返回Extensible.GetExtensionObject(ref extensionObject,createIfMissing);
}
}
公共静态无效更新(OptionData op)
{
使用(var fs=File.Create(probuffile))
{
Serializer.SerializeWithLengthPrefix(fs,op,PrefixStyle.Base128,3);
}
}
公共静态无效更新(存档弧)
{
使用(var fs=File.Create(probuffile))
{
Serializer.SerializeWithLengthPrefix(fs,arc,PrefixStyle.Base128,2);
}
}
公共静态无效刷新(参考OptionData op)
{
if(File.Exists(probuffile))
{
使用(var fs=File.OpenRead(probuffile))
{
op=Serializer.DeserializeWithLengthPrefix(fs,PrefixStyle.Base128,3);
}
}
}
公共静态无效刷新(参考存档弧)
{
if(File.Exists(probuffile))
{
使用(var fs=File.OpenRead(probuffile))
{
arc=Serializer.DeserializeWithLengthPrefix(fs,PrefixStyle.Base128,2);
}
}
}

我很乐意提供帮助,但我正努力让它失败。您说“但它几乎总是失败”,但以下可运行控制台exer工作正常,并写入各种大小的大范围数据:

using ProtoBuf;
using System;
using System.Collections.Generic;
using System.IO;
static class P
{
    static void Main()
    {
        var random = new Random(12345);
        // start with 100
        var archive = CreateData(random, 100);
        Update(archive);
        Refresh(ref archive);

        // make it bigger
        archive = CreateData(random, 200);
        Update(archive);
        Refresh(ref archive);

        // make it smaller
        archive = CreateData(random, 50);
        Update(archive);
        Refresh(ref archive);

        // go wild
        for (int i = 0; i < 1000; i++)
        {
            archive = CreateData(random, random.Next(0, 500));
            Update(archive);
            Refresh(ref archive);
        }

    }
    static Archive CreateData(Random random, int dataCount)
    {
        var archive = new Archive();
        var data = archive.data;
        for (int i = 0; i < dataCount; i++)
        {
            data.Add(new ArchiveData
            {
                period = random.Next(10000),
                sourcefolder = CreateString(random, 50),
                destinationfolder = CreateString(random, 50)
            });
        }
        return archive;
    }

    private static unsafe string CreateString(Random random, int maxLength)
    {
        const string Alphabet = "abcdefghijklmnopqrstuvwxyz0123456789";
        int len = random.Next(maxLength + 1);
        char* chars = stackalloc char[len];
        for (int i = 0; i < len; i++)
        {
            chars[i] = Alphabet[random.Next(Alphabet.Length)];
        }
        return new string(chars, 0, len);
    }

    static string probuffile = "my.bin";
    public static void Refresh(ref Archive arc)
    {
        if (File.Exists(probuffile))
        {
            using (var fs = File.OpenRead(probuffile))
            {
                arc = Serializer.Deserialize<Archive>(fs);
                Console.WriteLine("Read: {0} items, {1} bytes", arc.data.Count, fs.Length);
            }
        }
    }

    public static void Update(Archive arc)
    {
        using (var fs = File.Create(probuffile))
        {
            Serializer.Serialize<Archive>(fs, arc);
            fs.SetLength(fs.Position);
            Console.WriteLine("Wrote: {0} items, {1} bytes", arc.data.Count, fs.Length);
        }
    }
}

[Serializable, ProtoContract(Name = @"Archive"), ProtoInclude(1, typeof(List<ArchiveData>))]
public partial class Archive : IExtensible
{
    [ProtoMember(1, IsRequired = true, OverwriteList = true, Name = @"data", DataFormat = DataFormat.Default)]
    public List<ArchiveData> data { get; set; }

    public Archive()
    {
        data = new List<ArchiveData>();
    }

    private IExtension extensionObject;
    IExtension IExtensible.GetExtensionObject(bool createIfMissing)
    {
        return Extensible.GetExtensionObject(ref extensionObject, createIfMissing);
    }
}
[ProtoContract]
public struct ArchiveData
{
    [ProtoMember(1, IsRequired = false, OverwriteList = true, Name = @"sourcefolder", DataFormat = DataFormat.Default)]
    [global::System.ComponentModel.DefaultValue("")]
    public string sourcefolder { get; set; }

    [ProtoMember(2, IsRequired = false, OverwriteList = true, Name = @"destinationfolder", DataFormat = DataFormat.Default)]
    [global::System.ComponentModel.DefaultValue("")]
    public string destinationfolder { get; set; }

    [ProtoMember(3, IsRequired = false, OverwriteList = true, Name = @"period", DataFormat = DataFormat.FixedSize)]
    [global::System.ComponentModel.DefaultValue((int)0)]
    public int period { get; set; }

    public ArchiveData(string sfolder = "", string dfolder = "", int priod = 0)
    {
        sourcefolder = sfolder;
        destinationfolder = dfolder;
        period = priod;
    }
}
使用ProtoBuf;
使用制度;
使用System.Collections.Generic;
使用System.IO;
静态P类
{
静态void Main()
{
var random=新随机(12345);
//从100开始
var archive=CreateData(随机,100);
更新(档案);
刷新(参考档案);
//把它弄大点
存档=创建数据(随机,200);
更新(档案);
刷新(参考档案);
//小一点
存档=创建数据(随机,50);
更新(档案);
刷新(参考档案);
//发狂
对于(int i=0;i<1000;i++)
{
archive=CreateData(随机,random.Next(0500));
更新(档案);
刷新(参考档案);
}
}
静态归档CreateData(随机、int-dataCount)
{
var archive=new archive();
var data=archive.data;
对于(int i=0;iArchive archive = new Archive();
//Add some ArchiveData.
Refresh(ref archive);
[Serializable, ProtoContract(Name = @"OptionData")]
public class OptionData : IExtensible
{
    [ProtoMember(1, IsRequired = false, OverwriteList = true, Name = @"StartWithWindows", DataFormat = DataFormat.Default)]
    [DefaultValue(false)]
    public bool StartWithWindows { get; set; }

    [ProtoMember(2, IsRequired = false, OverwriteList = true, Name = @"AutoBackup", DataFormat = DataFormat.Default)]
    [DefaultValue(false)]
    public bool AutoBackup { get; set; }

    [ProtoMember(3, IsRequired = false, OverwriteList = true, Name = @"Speed", DataFormat = DataFormat.FixedSize)]
    [DefaultValue((int)0)]
    public int Speed { get; set; }

    private IExtension extensionObject;
    IExtension IExtensible.GetExtensionObject(bool createIfMissing)
    {
        return Extensible.GetExtensionObject(ref extensionObject, createIfMissing);
    }
}

public static void Update(OptionData op)
{
    using (var fs = File.Create(probuffile))
    {
        Serializer.SerializeWithLengthPrefix(fs, op, PrefixStyle.Base128, 3);
    }
}

public static void Update(Archive arc)
{
    using (var fs = File.Create(probuffile))
    {
        Serializer.SerializeWithLengthPrefix<Archive>(fs, arc, PrefixStyle.Base128, 2);
    }
}

public static void Refresh(ref OptionData op)
{
    if (File.Exists(probuffile))
    {
        using (var fs = File.OpenRead(probuffile))
        {
            op = Serializer.DeserializeWithLengthPrefix<OptionData>(fs, PrefixStyle.Base128, 3);
        }
    }
}

public static void Refresh(ref Archive arc)
{
    if (File.Exists(probuffile))
    {
        using (var fs = File.OpenRead(probuffile))
        {
            arc = Serializer.DeserializeWithLengthPrefix<Archive>(fs, PrefixStyle.Base128, 2);
        }
    }
}
using ProtoBuf;
using System;
using System.Collections.Generic;
using System.IO;
static class P
{
    static void Main()
    {
        var random = new Random(12345);
        // start with 100
        var archive = CreateData(random, 100);
        Update(archive);
        Refresh(ref archive);

        // make it bigger
        archive = CreateData(random, 200);
        Update(archive);
        Refresh(ref archive);

        // make it smaller
        archive = CreateData(random, 50);
        Update(archive);
        Refresh(ref archive);

        // go wild
        for (int i = 0; i < 1000; i++)
        {
            archive = CreateData(random, random.Next(0, 500));
            Update(archive);
            Refresh(ref archive);
        }

    }
    static Archive CreateData(Random random, int dataCount)
    {
        var archive = new Archive();
        var data = archive.data;
        for (int i = 0; i < dataCount; i++)
        {
            data.Add(new ArchiveData
            {
                period = random.Next(10000),
                sourcefolder = CreateString(random, 50),
                destinationfolder = CreateString(random, 50)
            });
        }
        return archive;
    }

    private static unsafe string CreateString(Random random, int maxLength)
    {
        const string Alphabet = "abcdefghijklmnopqrstuvwxyz0123456789";
        int len = random.Next(maxLength + 1);
        char* chars = stackalloc char[len];
        for (int i = 0; i < len; i++)
        {
            chars[i] = Alphabet[random.Next(Alphabet.Length)];
        }
        return new string(chars, 0, len);
    }

    static string probuffile = "my.bin";
    public static void Refresh(ref Archive arc)
    {
        if (File.Exists(probuffile))
        {
            using (var fs = File.OpenRead(probuffile))
            {
                arc = Serializer.Deserialize<Archive>(fs);
                Console.WriteLine("Read: {0} items, {1} bytes", arc.data.Count, fs.Length);
            }
        }
    }

    public static void Update(Archive arc)
    {
        using (var fs = File.Create(probuffile))
        {
            Serializer.Serialize<Archive>(fs, arc);
            fs.SetLength(fs.Position);
            Console.WriteLine("Wrote: {0} items, {1} bytes", arc.data.Count, fs.Length);
        }
    }
}

[Serializable, ProtoContract(Name = @"Archive"), ProtoInclude(1, typeof(List<ArchiveData>))]
public partial class Archive : IExtensible
{
    [ProtoMember(1, IsRequired = true, OverwriteList = true, Name = @"data", DataFormat = DataFormat.Default)]
    public List<ArchiveData> data { get; set; }

    public Archive()
    {
        data = new List<ArchiveData>();
    }

    private IExtension extensionObject;
    IExtension IExtensible.GetExtensionObject(bool createIfMissing)
    {
        return Extensible.GetExtensionObject(ref extensionObject, createIfMissing);
    }
}
[ProtoContract]
public struct ArchiveData
{
    [ProtoMember(1, IsRequired = false, OverwriteList = true, Name = @"sourcefolder", DataFormat = DataFormat.Default)]
    [global::System.ComponentModel.DefaultValue("")]
    public string sourcefolder { get; set; }

    [ProtoMember(2, IsRequired = false, OverwriteList = true, Name = @"destinationfolder", DataFormat = DataFormat.Default)]
    [global::System.ComponentModel.DefaultValue("")]
    public string destinationfolder { get; set; }

    [ProtoMember(3, IsRequired = false, OverwriteList = true, Name = @"period", DataFormat = DataFormat.FixedSize)]
    [global::System.ComponentModel.DefaultValue((int)0)]
    public int period { get; set; }

    public ArchiveData(string sfolder = "", string dfolder = "", int priod = 0)
    {
        sourcefolder = sfolder;
        destinationfolder = dfolder;
        period = priod;
    }
}