簡體   English   中英

當參數類型是基類時,將Derived類作為參數傳遞給方法

[英]Passing Derived class as a parameter to a method when the parameter type is base class

我是一個新手,並試圖理解繼承和設計模式的概念。

當我瀏覽一些博客時,我遇到了這種模式http://en.wikipedia.org/wiki/Strategy_pattern

我發現它很有趣,想要了解更多。 所以我開發了以下程序。

static void Main(string[] args)
{
    Context context;

    // Three contexts following different strategies
    context = new Context(new ConcreteStrategyAdd());
    int resultA = context.executeStrategy(3, 4);

    context = new Context(new ConcreteStrategySubtract());
    int resultB = context.executeStrategy(3, 4);

    context = new Context(new ConcreteStrategyMultiply());
    int resultC = context.executeStrategy(3, 4);

    Console.Read();
}      

abstract class Strategy
{
    public abstract int execute(int a, int b);

    public void Test()
    {
        Console.Write("tttt");
    }
}

class ConcreteStrategyAdd : Strategy
{
    public override int execute(int a, int b)
    {
        Console.WriteLine("Called ConcreteStrategyAdd's execute()");
        return a + b;  // Do an addition with a and b
    }
}

class ConcreteStrategySubtract : Strategy
{

    public override int execute(int a, int b)
    {
        Console.WriteLine("Called ConcreteStrategySubtract's execute()");
        return a - b;  // Do a subtraction with a and b
    }
}

class ConcreteStrategyMultiply : Strategy
{
    public override int execute(int a, int b)
    {
        Console.WriteLine("Called ConcreteStrategyMultiply's execute()");
        return a * b;   // Do a multiplication with a and b
    }
}

class Context
{
    private Strategy strategy;

    // Constructor
    public Context(Strategy strategy)
    {
        this.strategy = strategy;
    }

    public int executeStrategy(int a, int b)
    {
        return strategy.execute(a, b);
    }
}

該程序編譯良好,正在工作。 但我的問題是,當Context構造函數期望基類作為參數時,如何將派生類作為參數傳遞? 鑄造是否隱含發生? 為什么編譯器沒有錯誤?

context = new Context(new ConcreteStrategyAdd());  

public Context(Strategy strategy)
{
    this.strategy = strategy;
}

簡單地說:

派生類(或子類) 其基類的實例。

因此,當您將ConcreteStrategyAdd的實例傳遞給構造函數時,您實際上是在傳遞一個Strategy對象。

沒有涉及鑄造。 類型層次結構允許這種類型的編程。 它允許程序員在代碼中使用多態

由於ConcreteStrategyAdd 一種策略,因此不需要任何轉換 - 它滿足了作為策略的所有要求。 這是多態性的原理。

也許需要一個更簡單的例子:

abstract class Fruit { }

class Apple : Fruit { }
class Orange : Fruit { }
class Melon : Fruit { }

class FruitBasket
{
    void Add(Fruit item) { ... }
}

FruitBasket basket = new FruitBasket();
basket.Add(new Apple()); // Apple IS A fruit
basket.Add(new Orange()); // Orange IS A fruit
basket.Add(new Melon()); // Melon IS A fruit

class Potato : Vegetable { }

basket.Add(new Potato()); // ERROR! Potato IS NOT A fruit.

派生類基類。 (這是繼承的整個概念:繼承定義了'是'關系)。

另外,請查看Liskov替換原則 :)

如果您使用比策略模式更簡單的示例,則更容易理解。

假設你有一個名為“Fruit”的類和一個名為“Apple”的類,它來自水果。 任何與Fruit一起使用的方法一般都可以與Apple或任何其他特定類型的水果一起使用

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM