0

我已经在子类和父类中实现了 ISerializable,如下所示:

class CircuitElement : ISerializable
{
    ...
    protected void ISerializable.GetObjectData(SerializationInfo info, StreamingContext context)
    {
        if (info == null)
            throw new ArgumentNullException("info");
        info.AddValue("ID", ID);
    }
}

class Bus : CircuitElement, ISerializable
{
    ...
    void ISerializable.GetObjectData(SerializationInfo info, StreamingContext context)
    {
        if (info == null)
            throw new ArgumentNullException("info");
        ((ISerializable)base).GetObjectData(info,context);
        info.AddValue("Voltage", Voltage);
        info.AddValue("BaseVoltage", BaseVoltage);
        info.AddValue("Location", Location);
    }
}

但是在子类Bus中,我遇到了错误Use of keyword base is not valid in this context。我知道我可以在父CircuitElement类上隐式实现接口,然后我不必担心转换,但我的印象是显式实现更适合这种情况(原因类似于此处介绍的原因:https://stackoverflow.com/a/143425/996592

有没有办法进行转换,或者我是否ISerializable隐式地在父类中实现接口?

4

2 回答 2

2

就个人而言,我不同意您所链接的答案中提出的观点。显式接口实现更成问题,这正是您给出的原因:它确实不能很好地与继承配合使用。

如果您要重新实现已显式实现的接口,则无法在重新实现相同接口的类型的对象上调用该实现,包括从该重新实现的代码中。

两种选择:

  • 请改用隐式接口实现。我个人通常觉得这更简单。我只在接口有成员时才使用显式接口实现,而当你考虑类本身时,这些成员实际上没有意义。

  • 继续使用显式接口实现,但使该实现调用受保护的虚拟方法。然后,您可以在派生类中覆盖该虚拟方法并调用基实现。

于 2012-11-22T07:14:52.267 回答
1

您不需要使用"base"关键字进行转换。实际上,您不能"base"在这种情况下使用关键字。如果你想包含父信息,你应该简单地调用基方法,如果你以隐式方式"base.GetObjectData" 实现"ISerializable"接口,它将调用具有调用者实例所有者的父方法。

这种行为是面向对象模型中的简单事物之一,您无法更改它。另一方面,您可以使用"virtual"关键字并尝试覆盖父方法(在这种情况下,我认为您不需要此方法)。

我认为您应该在 stackoverflow 上查看这里,关于实现接口的方式有一些很好的答案。

在 MSDN 上还有一本关于多态性完美手册。它将帮助您了解为什么不能转换"base",并且您会找到一些技术以其他指定的方式进行转换。

我的点子:

使用"dynamic"关键字 and"ExpandoObject"是创建动态模型并在其上执行序列化操作的更好主意。在我个人看来,它在许多情况下要快得多,而且实现起来也很简单。

希望它有所帮助。

于 2012-11-22T07:24:02.037 回答