应用于基类和派生类的相同模板方法接口

本文关键字:模板方法 接口 基类 派生 应用于 | 更新日期: 2024-09-24 20:03:36

我有点难以用语言清楚地解释这个问题,所以我将立即从代码开始:

public interface ITemplate
{
    bool DoSomething(string a);
}
public class Worker
{
    public void DoSomeWork(ITemplate subcontractor)
    {
        try {
            //Do some work...
            if(subcontractor.DoSomething("hello"))
            {
                //Do some more work
            }
        }
        catch(InvalidOperationException) {/*...*/}
        //catch(Exception2) {/*...*/}
        //catch(Exception3) {/*...*/}
        //catch(Exception4) {/*...*/}
    }
}
public class BaseClass : ITemplate
{
    public void myFunction1()
    {
        Worker worker = new Worker();
        worker.DoSomeWork(this);   
    }
    public bool DoSomething(string a)
    {
        //Some code here
        return true;
    }
}
public class DerivedClass : BaseClass, ITemplate
{
    public void myFunction2()
    {
        Worker worker = new Worker();
        worker.DoSomeWork(this);   
    }
    public bool DoSomething(string a)
    {
        //Some other code here
        return true;
    }
}

使用这种结构,如果我调用 myDerivedClass.myFunction1()worker.DoSomeWork() 函数将执行DerivedClass.DoSomething(),但我希望在该上下文中执行BaseClass.DoSomething(),我该怎么办?

也许不可能通过模板方法设计模式实现我在这种情况下尝试做的事情。

最初的问题是我需要一种方法来执行代码,但是这段代码的某些部分是代码,根据调用该方法的对象而可变。有没有另一种方法可以在没有if(typeOf(subcontractor) == ...)的情况下做到这一点,这不是一个很好的做法,我希望代码的可变部分在调用者对象中存储和执行。

我可以在参数中传递委托或其他东西而不是发送整个调用者对象吗? 我不太习惯使用委托/等,但我认为这对我的问题有帮助,对吗?

谢谢乔纳森

应用于基类和派生类的相同模板方法接口

这是正确的行为,也是多态性的工作方式。如果您有派生类DerivedClass的实例,并且重写了方法(例如 DoSomething(,则在处理派生类型的实例时,基类代码中对方法DoSomething的所有调用都将通过派生类中的重写方法。

如果您希望执行基类中的代码,则需要不重写该方法,或者从派生类调用基类方法:

public class BaseClass
{
    public virtual void MyMethod() 
    { 
        // Do some stuff...
    }
}
public class DerivedClass : BaseClass
{
    public override void MyMethod()
    {
        // Do something new...
        // Do the stuff in BaseClass.MyMethod()
        base.MyMethod(); 
    }
}

>DerivedClass是一个ITemplate,因为它继承自BaseClass,这是一个ITemplate。 您不需要DerivedClass即可直接实现ITemplate

此外,如上所述,您发布的代码将无法编译。

public interface ITemplate
{
    bool DoSomething(string a);
}
public class Worker
{
    public void DoSomeWork(ITemplate subcontractor)
    {
        //Do some work...
        if(subcontractor.DoSomething("hello"))
        {
            //Do some more work
        }
    }
}
public BaseClass : ITemplate
{
    public void myFunction1()
    {
        Worker worker = new Worker();
        worker.DoSomeWork(this);   
    }
    public bool DoSomething(string a)
    {
        //Some code here
    }
}
public DerivedClass : BaseClass
{
    public void myFunction2()
    {
        Worker worker = new Worker();
        worker.DoSomeWork(this);   
    }
}