4

有没有办法在 C# 中序列化整个数组,例如:

[Serializable()]
public class Data
{
    public short Some_Short_Data = new short[100,100];
    public string Some_String_Data = new string[100,100];
}

然后写入文件:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;


using System.Xml;
using System.Xml.Serialization;
using System.IO;

Data Write_Data = new Data();

XmlSerializer Writer = new XmlSerializer(typeof(Data));

    using (FileStream file = File.OpenWrite("Myfile.xml"))
    {
        Writer.Serialize(file, Write_Data); //Writes data to the file
    }

当我尝试这个时,它失败了: XmlSerializer Writer = new XmlSerializer(typeof(Data));

说:“反映类型‘数据’时出现错误”

我对 Stack 和 Xml/Xml 序列化都特别陌生,因此将不胜感激。

4

3 回答 3

4

XmlSerialzier 不支持多维数组。但是您可以通过使用类似这样的临时类来解决问题

public class Array100<T>
{
    public T[] Data = new T[100];
}

public class Data
{
    public Array100<short>[] Some_Short_Data = new Array100<short>[100];
    public Array100<string>[] Some_String_Data = new Array100<string>[100];
}

顺便说一句:不需要Serializable属性。XmlSerialzier 不使用它

于 2013-04-30T21:17:41.573 回答
3

您不能序列化 int[,],但可以序列化 int[][]。在序列化您的二维数组之前,只需将其转换为像这样的锯齿状数组:

var my2dArray = new int[2,5];
var myJaggedArray = new int [2][];

for(int i = 0 ; i < my2DArray.GetLength(0) ; i ++)
{
    myJaggedArray[i] = new int[my2DArray.GetLength(1)];

    for(int j = 0 ; j < my2DArray.GetLength(1) ; j ++)
        myJaggedArray[i][j] = my2DArray[i,j]; 
}
于 2015-07-27T07:52:49.453 回答
0

我在尝试序列化作为对象字典中的值之一的多维数组时遇到了这个问题。我采用的方法是在序列化之前将所有数组包装在一个可序列化的类中,然后再将它们全部解包。

如果您不关心数据是什么样子,那么您可以使用二进制格式化程序序列化对象,该格式化程序可以序列化任何标记为可序列化的内容,然后将二进制数据保存为 base 64 编码字符串。

包装器实现如下。

[Serializable]
public class UnserializableValueWrapper: IXmlSerializable
{
    private static readonly BinaryFormatter Formatter = new BinaryFormatter();

    public UnserializableValueWrapper([NotNull] object value)
    {
        if (value == null)
        {
            throw new ArgumentNullException("value");
        }

        this.Value = value;
    }

    public UnserializableValueWrapper()
    {
    }

    public object Value { get; private set; }

    public XmlSchema GetSchema()
    {
        return null;
    }

    public void ReadXml(XmlReader reader)
    {
        reader.ReadStartElement();

        var length = int.Parse(reader.GetAttribute("length"));
        reader.ReadStartElement("Data");

        var buffer = new byte[length];
        reader.ReadContentAsBase64(buffer, 0, length);
        using (var stream = new MemoryStream(buffer))
        {
            this.Value = Formatter.Deserialize(stream);
        }

        reader.ReadEndElement();
        reader.ReadEndElement();
    }

    public void WriteXml(XmlWriter writer)
    {
        writer.WriteStartElement("Data");

        using (var stream = new MemoryStream())
        {
            Formatter.Serialize(stream, this.Value);
            var buffer = stream.ToArray();
            writer.WriteAttributeString("length", buffer.Length.ToString());
            writer.WriteBase64(buffer, 0, buffer.Length);
        }

        writer.WriteEndElement();
    }
}
于 2016-10-27T02:44:06.710 回答