C#序列化一个没有无参数构造函数的类

时间:2013-03-04 22:05:34

标签: c# serialization bouncycastle

我正在为3种不同的加密类实现工厂模式。工厂将确定要创建哪一个,然后从数据库中获取正确类的序列化实例并将其返回给请求者。 现在我正在编写类以将它们存储在数据库中。我正在为一个名为BouncyCastle的PGP加密类编写一个。我可以从文件创建类和键,但是当我尝试序列化时,它表示两个成员变量(类PgpPublicKeyPgpPrivateKey的对象)无法序列化,因为它们确实没有无参数构造函数。

public void createdBouncyFromFiles()
{
    var bc = new BouncyCastle("C:\\TestFiles\\BouncyPublicKey.txt", "C:\\TestFiles\\BouncyPrivateKey.txt", "Password1");
    var xmlSerializer = new XmlSerializer(bc.GetType());
    var textWriter = new StringWriter();
    xmlSerializer.Serialize(textWriter, bc);
    var theSerializedClass = textWriter.ToString();
}

该类有两个成员变量是问题所在。

public class BouncyCastle : ICryptographyProvider
{

    public PgpPublicKey m_publicKey;
    public PgpPrivateKey m_privateKey;
    public string m_passPhrase;
    // cut out the irelevant parts

这是公钥类。没有无参数构造函数。

public class PgpPublicKey
{
    public PgpPublicKey(PublicKeyAlgorithmTag algorithm, AsymmetricKeyParameter pubKey, DateTime time);
    // cut other methods
}

5 个答案:

答案 0 :(得分:27)

任何Serializer类都需要一个无参数构造函数,因为在反序列化时会创建一个空的新实例,然后它会复制从seialized数据中获取的每个公共属性。

如果您想避免在没有参数的情况下创建构造函数,可以轻松地将构造函数设为私有。

EX:

public class PgpPublicKey
{
    public PgpPublicKey(PublicKeyAlgorithmTag algorithm, AsymmetricKeyParameter pubKey, DateTime time);

    private PgpPublicKey();
    // cut other methods
}

答案 1 :(得分:4)

是的,XmlSerializer 需要无参数构造函数才能使序列化工作。

从以下答案:Why XML-Serializable class need a parameterless constructor

  

在对象的反序列化期间,负责的类   反序列化对象会创建序列化类的实例   然后继续填充序列化的字段和属性   只有在获得填充实例后才能填充。

     

如果需要,您可以将构造函数设置为私有或内部,就这样   只要它无参数。

答案 2 :(得分:2)

DataContractSerializer不需要无参数构造函数。它需要的是类的特殊属性。

答案 3 :(得分:0)

您是否定义了PgpPublicKeyPgpPrivateKey个类?只需向它们添加无参数构造函数。

如果您不想让它们从外部访问,它们可以是私有的。解串器仍然可以访问它们。

答案 4 :(得分:0)

对于几年后仍在寻找的任何人,答案现在是FormatterServices.GetUninitializedObject。小心一点,因为这只是设置为所有零和零的内存,并且如果对象的默认值中的字段不是零,则可能设置为错误:“因为初始化了对象的新实例设置为零且不运行任何构造函数,则该对象可能不表示该对象认为有效的状态。”