2011-12-09 247 views
1

我最近一直在研究类继承,并且不断遇到这段特定的代码。创建“派生类”类型的对象

public class Foo {  

public bool DoSomething() 
{ 
    return false; 
} 
} 

public class Bar : Foo { 

public new bool DoSomething() 
{ 
    return true; 
} 
} 

public cass Test { 

    public static void Main() { 

    Foo test = new Bar(); 

    Console.WriteLine (test.DoSomething());  
    } 
} 

什么这里让我困惑的是,如果是我,我会按类型酒吧酒吧创建的实例...

Bar test = new Bar(); 

我不明白为什么它会被创建的方式它在代码中。

+1

您寻求的答案在于BrokenGlass的答案和Justin的答案混合在多态性中。不幸的是,这样的语义没有简单的答案。您需要熟悉工厂模式,IoC或依赖注入。工厂模式可能是最简单的一种。没有经验,你需要一本书来打破复杂的细节。首先设计模式是一个很好的选择。 –

回答

3

此代码可能写演示之间的区别覆盖隐藏一个基类方法:

在这种情况下,实例使用一个Bar对象Foo变量将使用基类方法DoSomething()并打印出false。有DoSomething方法被声明为在基类虚拟和在派生类被覆盖的输出将是true如下面的例子:具有较少通用

public class Foo {  

public virtual bool DoSomething() 
{ 
    return false; 
} 
} 

public class Bar : Foo { 

public override bool DoSomething() 
{ 
    return true; 
} 
} 
+0

我知道代码的目的,但我不明白的是在创建子类的实例时使用超类作为参考。真的有什么好处,如果超类方法是虚拟的,它会有什么不同吗? – Zizo47

+0

大多数其他答案都会涉及使用基类(和/或接口)而不是具体类的好处 - 它取决于抽象而不是具体的东西,所以稍后可以更改实际的实现 - 这是多态性的基础,并使IoC/Dependency Injection等功能更加强大 – BrokenGlass

0

一般来说,它不会。一个更现实的例子是

void DoSomethingWithAFoo(Foo f) { 
    f.DoSomething(); 
} 

在这种情况下,f可能是FooBar,并且DoSomethingWithAFoo不必知道或关心。

0

Bar来自Foo,因此创建Bar的实例并将其分配给Foo-参照是完全有效的。我怀疑你已经显示的示例代码只是显示BarFoo,因此可以赋值。

1

在现实世界中更容易想到这些东西。

试着想着一辆车。您可以拥有不同的车型/车型,但每辆车都具有相同的基本功能。

你的代码可以用相同的方式处理对象。你写的代码与任何车上班,但你真的可以指定汽车的任何你想要的品牌/型号:

public class Car 
{ 
    public virtual void Drive() 
    { 
    } 
} 

public class ChevyVolt : Car 
{ 
    public override void Drive() 
    { 
     // Initialize the battery and go 
    } 
} 

public class CadillacEscalade : Car 
{ 
    public override void Drive() 
    { 
     // Check to ensure you have an oil field worth of gas and go 
    } 
} 

现在,这些定义...你可以创建负责驾驶的汽车类。什么车都没关系。你只需要担心驾驶:

public class Commuter 
{ 
    public void GoToWork() 
    { 
     // Garage.PickCar() could return either ChevyVolt or an Escalade 
     Car todaysRide = Garage.PickCar(); 

     // Now that we have a car, go to work 
     todaysRide.Drive(); 
    } 
} 
0

可以分配一个更通用的(富)类型(Boo)这通常是在您利用多态时完成的。经典的例子是有Animal,Dod和Cat,然后你可以说Animal=new Dog()Animal=new Cat(),那么你可以调用它的虚拟函数并自动调用正确的函数。这是不是你的情况,因为你是重叠功能DoSomething与新...

0

如果你认为它只想要Foo定义的功能Bar实现,它可能会更有意义。 Bar可以自由添加更多与Bar相关的功能。

public class Bar : Foo { 

public new bool DoSomething() 
{ 
    return true; 
} 

public bool IsValid {get;} 
} 

现在调用代码只在乎通过Foo这样定义的抽象,尽管你正在创建Bar,你获得通过Foo(只DoSomething)中定义的合同,因此不Bar.IsValid功能我只是定义。

相关问题