了解继承

时间:2015-02-05 12:18:10

标签: c# oop inheritance

namespace WebApplication1.Class
{
    public class DailySalaryCalculator
    {
        public void Calculate()
        {
        }
    }

    public class WeeklySalaryCalculator : DailySalaryCalculator
    {
        public void Calculate()
        {
        }
    }

    public class MonthlySalaryCalculator : WeeklySalaryCalculator
    {
        public void Calculate()
        {
            //I want to execute Calculate() of Daily Salary Calculator here.
        }
    }
}

我想直接从Calculate拨打DailySalaryCalculator MonthlySalaryCalculator方法而不创建DailySalaryCalculator的对象。

我该怎么做?

先谢谢

3 个答案:

答案 0 :(得分:1)

您的代码是继承的不当使用。首先,您需要了解您要完成的任务,在这种情况下,您需要计算工资。每日,每周或每月是进行计算的策略。

您应该将每个类视为用于实现计算的业务规则的封装。每周没有设计意义继承每日,同样是每月和每周。

更好的方法是

public abstract AbstractSalaryCalculator
{
     //note that the calculation returns something, as this is basically a service
     public virtual decimal Calculate();
 }

 public class DailySalaryCalculator:AbstractSalaryCalculator
 {
    public override decimal Calculate()
    {
         //do stuff
        //return result
    }
 }

 public class WeeklySalaryCalculator:AbstractSalaryCalculator
 {
       public override decimal Calculate()
    {
         //do stuff
        //return result
    } 
 }

public class MonthlySalaryCalculator:AbstractSalaryCalculator
 {
     //probably is better for the daily calculator to be injected via the constructor
     public override decimal Calculate(DailySalaryCalculator daily)
    {
         //use daily to do stuff
        //return result
    } 
 }

var daily= new DailySalaryCalculator();
var monthly=new MonthlySalaryCalculator();
var result=monhtly.Calculate(daily);

说明

重点是定义处理业务规则特定方面的计算器,然后以解耦的方式(重新)使用它们。所有都是计算器,但每周不是每日。每周/每月可以使用每日,因为这是这些概念之间的关系。

继承意味着孩子 是父母的更具体的概念。在您的使用案例中,没有更具体的内容,它们只是计算薪水的不同方式。 这就是为什么在我的代码中,每月calc 使用作为每日一个,但它不会继承它。

答案 1 :(得分:0)

您可以通过以下代码段来实现它,

只需 使用DailySalaryCalculator类投射当前对象

public class DailySalaryCalculator
{
    public void Calculate()
    {

    }
}

public class WeeklySalaryCalculator : DailySalaryCalculator
{
    public void Calculate()
    {

    }
}

public class MonthlySalaryCalculator : WeeklySalaryCalculator
{
    public void Calculate()
    {
        (this.MemberwiseClone() as DailySalaryCalculator).Calculate();
    }
}

我不确定你尝试了什么。

但下面是我的示例代码。

class Program
{
    private static void Main(string[] args)
    {
        MonthlySalaryCalculator obj = new MonthlySalaryCalculator();

        obj.Calculate();

        Console.Read();
    }
}

public class DailySalaryCalculator
{
    public void Calculate()
    {
        Console.WriteLine("DailySalaryCalculator");
    }
}

public class WeeklySalaryCalculator : DailySalaryCalculator
{
    public void Calculate()
    {
        Console.WriteLine("WeeklySalaryCalculator");
    }
}

public class MonthlySalaryCalculator : WeeklySalaryCalculator
{
    public void Calculate()
    {
        (this.MemberwiseClone() as DailySalaryCalculator).Calculate();
    }
}

答案 2 :(得分:0)

您可以通过overriding原始Calculate()方法实现该目标,该方法必须声明为Virtual(以允许在继承类中覆盖它)。

要保留原始方法的代码并向其中添加内容,您应使用base关键字来调用原始方法的行为。

您的代码应如下所示:

namespace WebApplication1.Class
{
    public class DailySalaryCalculator
    {
        public virtual void Calculate()
        {
        }
    }

    public class WeeklySalaryCalculator : DailySalaryCalculator
    {
        public override void Calculate()
        {
        }
    }

    public class MonthlySalaryCalculator : WeeklySalaryCalculator
    {
        public override void Calculate()
        {
            //I want to execute Calculate() of Daily Salary Calculator here.
            //Yes do this :

            base.Calculate();

            //Now, Add your additional code here
        }
    }
}

注意!! :您不需要在virtual的{​​{1}}方法中重新编写关键字WeeklySalaryCalculator,因为answer解释得很好:

  

您可以将某个方法声明为虚拟一次,但您可以   根据需要多次覆盖它 - 覆盖不是最终的,并且   它不限制从第一个覆盖继承的类   类。