自定义结构体,使其序列化为Int32类型

本文关键字:Int32 类型 序列化 结构体 自定义 | 更新日期: 2023-09-27 18:04:02

我使用二进制序列化保存数据。现在我已经将程序中的一个字段从Int32更改为结构体。但我仍然想保存字段为Int32向后兼容。我怎么做呢?

我的程序是从Delphi移植过来的,使用了很多数组。问题是Delphi中的列表从1开始计数,当我现在用c#开发时,vilkort使跟踪索引变得困难。因此,我使用了一个结构体,以便更容易地处理基于0的数组的基于1的索引,直到我纠正了整个程序。

    public void Save()
    {
            using (var writer = File.Open(Path, FileMode.Create))
            {
                var serializer = new BinaryFormatter();
                serializer.Serialize(writer, _data);
            }
    }
    private void Load()
    {
        using (var reader = File.Open(Path, FileMode.Open))
        {
                var deserializer = new BinaryFormatter();
                _data = (Foo) deserializer.Deserialize(reader);
        }
    }
public struct Indexer
{
    //0-baserat index
    private int _index;
    public Indexer(int index)
    {
        _index = index;
    }
    static public implicit operator Indexer(int index)
    {
        return new Indexer(index);
    }
    static public implicit operator int(Indexer indexer)
    {
        return indexer._index;
    }
    public override string ToString()
    {
        return (_index + 1).ToString();
    }
    ...
  }

自定义结构体,使其序列化为Int32类型

您可以添加Int32类型的遗留字段,并且还具有struct字段。使用[OnDeserialized]属性(和正确的参数)创建一个方法,并在某些情况下从int字段初始化struct字段,例如,int字段是非零的,并且struct在反序列化后具有默认值,表明数据来自旧格式。

private int intValue;                // Legacy field
private SomeStruct structValue;      // New field
[OnDeserialized]
private void OnDeserialized(StreamingContext context)
{
  if (intValue != 0)
  {
      // Old format, initialize struct with int value.
      structValue = new SomeStruct(intValue);
  }
}

这不是很优雅,还有其他的方法,但如果你不介意保留两个字段,这是一个更简单的方法。注意,上面的代码假设零表示旧int字段的"缺失"值。

我想唯一的方法是有两个类-一个具有结构体,一个具有int32。然后可以在序列化之后将其中一个转换为另一个。

 int n = YourStruct.SomeIntVar;
 Marshal.WriteInt32(hBuffer, n);

我不确定这是否适用于您的情况,因为这取决于您如何将数据序列化到存档中。如果您直接操作内存或共享内存(hBuffer)上的数据,上面的代码片段应该会有所帮助。

isserializersurrogate

这将允许您控制序列化/反序列化过程。

相关文章: