Шаблоны Decorator + State: что, если метод, который я декорирую, зависит от состояния объекта? - PullRequest
0 голосов
/ 16 апреля 2020

Класс P C имеет несколько методов - turnON (), turnOFF () и doWork (). Метод doWork () можно оформить, добавив дополнительные функции в P C.

Каждый метод меняет свое поведение в зависимости от состояния P C - поэтому, когда вы пытаетесь включить ON () P C, метод просто делегирует выполнение поведения текущему состоянию P C, и он обрабатывает его правильно.

Однако, если я хочу иметь doWork (), метод, который может быть оформлен, также зависит от состояния (P C не может сделать doWork () что делать, если указано состояние PCStateOFF или PCStateIncomplete)?

Поскольку в шаблоне состояния указано, что выполнение поведения должно быть делегировано состоянию, необходимо, чтобы PCStateON, PCStateOFF и PCStateIncomplete также обрабатывали doWork (). Но если его P C, который украшен, то я не проверяю, включен ли P C перед выполнением добавленной функциональности. Я мог бы внедрить некоторые операторы if / else внутри каждой реализации PCWecorators doWork (), чтобы добавить функциональность только в том случае, если текущее состояние это то, что позволяет, но тогда вся идея State заключается в том, чтобы покончить с if / else.

Тогда я мог бы на самом деле украсить класс PCStateON, так как это единственный, который изменяется, когда украшен P C ...

Как мне выполнить это правильно?

Общий интерфейс для P C и PCDecorator:

interface IPC {
    public void doWork();
}

Класс P C:

public class PC implements IPC {

    PCState state;

    public PC(){
        this.state = new PCStateIncomplete(this);
    }

    public void turnOn(){
        this.state.turnOn();
    }

    public void turnOff(){
        this.state.turnOff();
    }

    public void changeState(PCState state){
        this.state = state;
    }

    public void doWork() {
        System.out.print("\nWorking... ");
    }
}

Общий класс Decorator и декораторы:

abstract public class PCDecorator implements IPC{
    protected IPC pc;
    abstract public void doWork();
}
public class PCGamingDecorator extends PCDecorator {
    public PCGamingDecorator(IPC computer) {
        this.pc = computer;
    }

    @Override
    public void doWork(){
        pc.doWork();
        System.out.print("Gaming... ");
    }
}
public class PCMiningDecorator extends PCDecorator{
    public PCMiningDecorator(IPC computer) {
        this.pc = computer;
    }

    @Override
    public void doWork(){
        pc.doWork();
        System.out.print("Mining... ");
    }
}
public class PCStreamingDecorator extends PCDecorator {
    public PCStreamingDecorator(IPC computer) {
        this.pc = computer;
    }

    @Override
    public void doWork(){
        pc.doWork();
        System.out.print("Streaming... ");
    }
}

Общее состояние и состояния:

public interface PCState {
    public void turnOn();
    public void turnOff();
}
public class PCStateIncomplete implements PCState {
    PC pc;
    public PCStateIncomplete(PC pc){
        this.pc = pc;
    }
    public void turnOn(){
        System.out.println("Cannot do Work - PC is Incomplete!");
    }
    public void turnOff(){
        System.out.println("Cannot turn OFF - PC is Incomplete!");
    }
}
public class PCStateOFF implements PCState {
    PC pc;
    public PCStateOFF(PC pc){
        this.pc = pc;
    }
    public void turnOn(){
        this.pc.changeState(new PCStateON(this.pc));
        System.out.println("PC has been turned ON!");
    }
    public void turnOff(){
        System.out.println("PC is already OFF!");
    }
}
public class PCStateON implements PCState {
    PC pc;
    public PCStateON(PC pc){
        this.pc = pc;
    }
    public void turnOn(){
        System.out.println("PC is already ON!");
    }
    public void turnOff(){
        this.pc.changeState(new PCStateOFF(this.pc));
        System.out.println("PC has been turned OFF!");
    }
}
...