Is this the correct implementation of the bridge pattern in Java?

I'm trying to improve my understanding of design patterns, and I'm a little confused about bridge patterns You can see my example below:

public interface Animal {
    public abstract void eat();
    public abstract void move();
}


public class Jaguar implements Animal{

    @Override
    public void eat() {
        System.out.println("The Jaguar eats meat");
    }

    @Override
    public void move() {
        System.out.println("The Jaguar runs");
    }
 }

public class Kangaroo implements Animal{

    @Override
    public void eat() {
        System.out.println("THe Kangaroo eats grass and other vegetables");
    }

    @Override
    public void move() {
        System.out.println("The Kangaroo hops around :)");
    }

}

public abstract class Environment {

    private Animal animal;

    public Environment(Animal animal){
        this.animal = animal;
    }

    public void someAnimalEats(){
        this.animal.eat();
    }

    public void someAnimalMoves(){
        this.animal.move();
    }

    public abstract void environmentPolutionStatus();
}


public class Australia extends Environment{

    public Australia(Animal animal) {
        super(animal);
    }

    @Override
    public void environmentPolutionStatus() {
        System.out.println("Australia is in good shape as far as polution is concerned.");
    }

}


public class Africa extends Environment{

    public Africa(Animal animal) {
        super(animal);
    }

    @Override
    public void environmentPolutionStatus() {
        System.out.println("Africa looks pretty good,however the hunting is kind of bad");

    }

}

public class BridgePatternMain {
    public static void main(String[] args){
        Environment australiaKangaroo = new Australia(new Kangaroo());
        Environment australiaJaguar = new Australia(new Jaguar());
        Environment africaKangaroo = new Africa(new Kangaroo());
        Environment africaJaguar = new Africa(new Jaguar());

        australiaKangaroo.environmentPolutionStatus();
        australiaKangaroo.someAnimalEats();
        australiaKangaroo.someAnimalMoves();

        australiaJaguar.environmentPolutionStatus();
        australiaJaguar.someAnimalEats();
        australiaJaguar.someAnimalMoves();

        africaKangaroo.environmentPolutionStatus();
        africaKangaroo.someAnimalEats();
        africaKangaroo.someAnimalMoves();

        africaJaguar.environmentPolutionStatus();
        africaJaguar.someAnimalEats();
        africaJaguar.someAnimalMoves();
    }
}

My question:

>Is this the correct bridge mode? > If the interface is replaced, can the bridge pattern abstract class be used (I saw this method in this tutorial) http://www.newthinktank.com/2012/10/bridge-design-pattern-tutorial/ )But according to this( https://dzone.com/articles/design-patterns-bridge )It seems that in my case, animals should not be an abstract class.. > Is it necessary to use the method someanimaleats() and someanimalmoves() in the environment class? More precisely, is it mandatory to correspond to each method in this class, the method from the animal interface?

Thank you.

Solution

>The domain you present (animals and their environment) is not a good use case for the bridge pattern It has a very specific purpose: to separate the abstract (including the extension of the abstract) from the implementation (and possibly the extension) One of the key features is the abstract reference implementation (the "bridge" in the name), rather than extending or implementing the abstract implementation Usually, the specific implementation is determined by the client at run time

It's not easy to imagine a natural use case of a bridge that simulates real-world objects such as animals and environments It's easier to think of classes designed to perform certain functions

// abstraction 
abstract class Logger {
    protected final logoutputter outputter;
    public abstract void log(String message);
}

// abstraction extension
class ErrorLogger extends Logger {
    public void log(String message) {
        outputter.output("Error: " + message);
    }
}

// implementation interface
interface logoutputter {
    void output(String message);
}

// implementation extensions
class Filelogoutputter implements logoutputter ...
class Consolelogoutputter implements logoutputter ...

The client may do the following:

Logger logger = new ErrorLogger(new Filelogoutputter("errors.log"));

>The class / interface combination I suggest I use in this example is quite typical You can create abstractions and interfaces, but considering that the bridge node is a reference implementation, it makes it easier to make it an abstract class. > I hope this example can also answer this question: you can use similar methods in abstraction and implementation, but it is certainly not necessary An interesting and useful aspect of this pattern is that different independent features (in this example, what is recorded and how it is recorded) can be individually defined as extensions of abstraction and implementation This allows you to mix and match features without losing control of the class structure The independence of these features (i.e. orthogonality) usually requires completely different methods in the two structures

The content of this article comes from the network collection of netizens. It is used as a learning reference. The copyright belongs to the original author.
THE END
分享
二维码
< <上一篇
下一篇>>