2009-06-11 68 views
4

几年前我创建了一个.NET应用程序,但没有考虑太多的文件格式:它使用soap格式化程序来序列化我们的大型对象层次结构。这很容易做,所以我没有多少考虑。如何选择文件格式?

考虑到以下问题,我现在试图想出一个更优化的文件格式: 保存文件时,它最终被转换为字节数组,并通过线路发送到数据库进行存储。这最终会成为一个大问题,因为你在内存中拥有所有对象,然后为序列化器分配更多内存,然后为字节数组分配更多内存。即使尺寸适中的对象图最终也会使用大量内存来保存文件。

我不知道如何既从一个文件格式的角度,也有可能从算法的角度来改善这种(对象 - >流 - >字节数组)

UPDATE: 我会在通过线路发送数据前,一直在压缩字节数组,所以虽然这是很好的建议,但它已经在我的应用程序中实现。

我确实从Soap转换为Binary Serialization,这产生了巨大的差异:我们的文件比以前小了大约7倍。 (当然,你的里程可能会有所不同)。

回答

4

如果您需要高效的序列化,并且不关心其序列化为二进制格式,只需使用.NET中的标准二进制序列化。你可以使用[Serializable]属性来修饰你的可序列化类型,并使用BinaryFormatter将你的对象序列化为byte []。

3

一个非常快速的解决方案,如果你还没有尝试过。这不会完全减少开销,但会有所帮助。

当您序列化对象时,请使用属性而不是节点。使用节点有很多浪费的空间。您可以通过在属性/字段上添加[XmlAttribute]标签来轻松完成此操作。

参考链接:http://msdn.microsoft.com/en-us/library/2baksw0z(VS.71).aspx

1

您还可以使用压缩/压缩流尝试,我想从记忆SharpZipLib允许您创建压缩码流。

0

为什么不将应用程序从XML移动到JSON?有很多库可以在.NET中序列化/反序列化JSON。

0

我已经使用LZMA进行数据压缩存储到数据库。例如,将事情从36,000提高到6000.使用起来非常简单,您不必将数据存储为二进制文件,也可以是字符串。

3

BinaryFormatter + DeflateStream =压缩持久对象

using System; 
using System.IO; 
using System.IO.Compression; 
using System.Runtime.Serialization.Formatters.Binary; 

namespace CompressedSerialized 
{ 
    class Program 
    { 
     static void Main(string[] args) 
     { 
      var obj1 = new MyObject() { Prop1 = "p1", Prop2 = "p2" }; 
      MyObject obj2 = null; 
      var bin = new BinaryFormatter(); 
      byte[] buffer = null; 

      using (var ms = new MemoryStream()) 
      { 
       using (var zip = new DeflateStream(ms, CompressionMode.Compress)) 
       { 
        bin.Serialize(zip, obj1); 
        zip.Flush(); 
       } 
       buffer = ms.ToArray(); 
      } 

      using (var ms = new MemoryStream(buffer)) 
      using (var unzip = new DeflateStream(ms, CompressionMode.Decompress)) 
      { 
       var des = bin.Deserialize(unzip); 
       obj2 = des as MyObject; 
      } 

     } 
    } 

    [Serializable] 
    public class MyObject 
    { 
     public string Prop1 { get; set; } 
     public string Prop2 { get; set; } 
    } 
}