在使用抽象基类作为参数实现接口方法时访问派生类属性

时间:2011-07-21 07:09:00

标签: c#

我努力寻找这个问题的答案,所以如果已经有人问过,也许我说错了。我有一个抽象基类和派生类。

abstract class Foo
{
   protected int property1
   protected int property2
// etc..
}

我的dervied类包含一些在基类中找不到的额外属性:

class Fum : Foo
{
   public int UniqueProperty { get; set; }
}

现在我有一个带有抽象基类的方法的接口:

interface IDoSomethingWithFoos
{
   void DoSomethingWithFoo(Foo fooey);
}

实现接口的类

class FumLover : IDoSomethingWithFoos
{
   void DoSomethingWithFoo(Foo fooey)
   {
      // now in here i know i am going to be passed objects of Fum
      // and i want to access its unique properties

      fooey.UniqueProperty = 1;   // this doesn't work

      ((Fum)fooey).UniqueProperty = 1;   // this seems to work

      // as does..

      Fum refToFum = fooey as Fum;
      refToFum.UniqueProperty = 1;

   }
}

所以我的问题是:我是否以正确的方式解决这个问题?虽然这个编译,我没有足够的代码来确保它实际上正常工作。我的另一个问题是:这是一个糟糕的设计吗?还有更好的方法吗?

*

详细说明一下,因为自然响应是,如果你要传递Fum,那么让接口方法采用Fum而不是Foo。

但是让我们说在我的FumLover类中,方法DoSomethingWithFoo使用抽象贝司类中的ARE属性处理95%。让我们说我有另一个名为Fie的派生类,它有几个独特的属性。现在假设我有一个FieLover类,我想实现DoSomethingWithFoo,因为我将要做的95%可以应用于所有Foo,但同样,有一点是Fie独有的。

有什么替代方案?为每个人提供一个接口:IDoSomethingWithFums,IDoSomethingWithFies等?似乎我失去了只有5%差异的所有抽象。

2 个答案:

答案 0 :(得分:4)

  // now in here i know i am going to be passed objects of Fum
  // and i want to access its unique properties

这是设计变更可能有所帮助的线索。您当前的界面显示“我正在使用Foo s”。如果实现只适用于Fum s,那么你所说的和你正在做的事情就不匹配了。如果您真的只期望Fum s,那么将接口中的参数声明为Fum

如果您不想这样做,那么最好使用as语法,因为当有人认为可以传入Foo时,您不会抛出异常(因为嘿) ,接口表示他们可以。)

as代码应如下所示:

Fum fumObj = fooey as Fum;
if (fumObj != null)
    fumObj.UniqueProperty = 1;

<强>更新

你对每个派生类的接口的建议实际上是可取的(因为他们说明了他们实际做了什么),但让我们退后一步:你实际上想要在这里完成什么?如果您希望IDoSomethingWithFoos利用Foo的位置作为基类(尽管是抽象的基类),那么您需要确保调用DoSomethingWithFoo对所有{{1}都有意义}}秒。如果没有,那么你已经输了,因为即使你声称是一个FooLover,你真的只爱Foo s(或Fum s。)

一种解决方案是在Fie本身上声明abstract DoSomething()方法。现在,您可以拥有Foo,并且代码如下:

List<Foo>

现在你实际上正在利用抽象。你不关心它们是什么类型的foreach (Foo foo in fooList) foo.DoSomething(); :它们都做了一些事情,可能是基于仅对派生类唯一的属性(不需要强制转换。)

答案 1 :(得分:-1)

我认为你所做的很好,因为Fum扩展了Foo你应该能够以你自己的方式投射它。

另一种方法是实现IFoo接口并将其传递给方法。