Decorator (decorator) pattern of java design pattern (8)

Decorator/decorator pattern of java design pattern⑧

Learn to shift your mood, because only in this way can you struggle from sorrow and make yourself happy.

Design pattern learning, I will blog about 23 design patterns in the near future , so stay tuned~
—2021/1/11

definition

Modification mode is a design mode that dynamically adds new behaviors to a class in the field of object-oriented programming. In terms of function, the modification mode is more flexible than generating subclasses, so that you can add some functions to an object instead of the entire class.

Baidu Encyclopedia

Application scenario

In the case that a class needs to add new features, without changing the current class,

For example, the function of a class is'fried rice', I want to add an'egg' function to this class, or add a'bacon' function to turn the original'fried rice' into'egg fried rice';

Role analysis

  • Abstract structure (Component) role : define an abstract interface to standardize objects that are ready to accept additional responsibilities
  • Concrete Component roles : implement abstract structures and add some responsibilities to them through decorative roles.
  • Abstract decoration (Decorator) role : inheritance or abstract construction, and include concrete construction examples, which can extend the concrete construction functions through its subclasses.
  • The role of Concrete Decorator : implement the relevant methods of abstract decoration and add additional responsibilities to the concrete construction object

Simple Analysis:

  • Abstract construction role: abstract class by decorator
  • Concrete structure role: implement the abstract class of the decorated device, the decorated device
  • Abstract decoration role: decorator abstract class
  • Specific decoration role: decorator, implement the decorator abstract class

Why define so many abstract classes?

Observe the principle of dependency inversion (interface-oriented programming)

analysis

UML类图(1.1):

  • Noodles
  • FriedRice
  • Food

Noodles and fried rice belong to food, so they are inherited from Food. We need to add some new products to each food.

For example, I want to add an egg

Now this food category has become the decorator, and the egg is decorated to achieve the effect of'noodle egg' or'fried rice egg', and the egg becomes the decorator

If originally a fried rice was 10 yuan and an egg was 1 yuan, I would order an egg fried rice to be 11 yuan

UML类图(1.2):


This is the final rendering that we are going to complete. It doesn't matter if this picture is not understood, let's take a look at the code first, and finally return to see this picture at a glance.

Code

Food category:

public abstract class Food {
    
    
    private String name;//名字
    private float price;//价格
    //总价
    public abstract float totalPrice();
    set...
    get...
}

FriedRice fried rice:

public class FriedRice extends Food {
    
    

    public FriedRice() {
    
    
        setName("炒饭");
        setPrice(12);
    }

    @Override
    public float totalPrice() {
    
    
        //调用父类的价格方法 将set的值获取出来 
        return getPrice();
    }
}

analysis:

代码流程图(2.1):


Here, if you call the FriedRice (Fried Rice) constructor, first assign the price of the fried rice.

Noodles:

public class Noodles extends Food {
    
    
    public Noodles() {
    
    
        setName("面食");
        setPrice(9);
    }
    @Override
    public float totalPrice() {
    
    
        return getPrice();
    }
}

Same as FriedRice (fried rice)

Implementation code:

//面条
Noodles noodles = new Noodles();

Log.i("装饰器模式", noodles.getName() + "\t" + 
			noodles.getPrice() + "\t总价:" + 
			noodles.totalPrice()
		);

//        炒饭
FriedRice friedRice = new FriedRice();

Log.i("装饰器模式", friedRice.getName() + "\t" + 
		friedRice.getPrice() + "\t总价:" + 
		friedRice.totalPrice()
	);

Log图(3.1):


This is very simple, I won't describe it, here is called the garnished, take an egg, let it become'egg noodles' or'egg fried rice', the egg here is the decorator.

GarnishFood decoration category:

public abstract class GarnishFood extends Food {
    
    

    Food food;

    public GarnishFood(Food food) {
    
    
        this.food = food;
    }
  	set..
  	get..
}

Egg eggs:

public class Egg extends GarnishFood{
    
    
    public Egg(Food food) {
    
    
        super(food);
        setName("鸡蛋");
        setPrice(1);
    }

    @Override
    public float totalPrice() {
    
    
        return  getPrice()+  getFood().totalPrice();
    }
}

Egg egg totalPrice() parameter analysis:

  • getPrice() Parameters :

    Red box: here getPrice() is set to 1 by the constructor.
    Yellow box: Because the egg class (Egg) inherits from the decoration class (GarnishFood), the decoration class inherits from Food, so the calls here are all top-level Methods in Food
  • getFood().totalPrice() parameter :

    here is also the Food method in the top parent class,
    so getFood().totalPrice() = total price

Use code:

Noodles nd = new Noodles();
Log.i("装饰器模式", nd.getName() + "\t" + 
			nd.getPrice() + "\t总价:" +
			 nd.totalPrice());

Egg egg = new Egg(nd);
Log.i("装饰器模式", egg.getName() + "\t" +
		 egg.getPrice() + "\t总价:" + 
		 egg.totalPrice());

Egg egg1 = new Egg(egg);
Log.i("装饰器模式", egg1.getName() + "\t" + 
		egg1.getPrice() + "\t总价:" + 
		egg1.totalPrice());

Log图(3.2): It
Insert picture description here
can be seen that without adding an egg, the total price is +1 yuan

If you can add new products now, for example, you can add bacon, let's see how to write the code~

Bacon Bacon:

public class Bacon extends GarnishFood{
    
    
    public Bacon(Food food) {
    
    
        super(food);
        setName("培根");
        setPrice(3.5f);
    }

    @Override
    public float totalPrice() {
    
    
        return super.getPrice() + super.getFood().totalPrice();
    }
}

Use code:

Bacon bacon = new Bacon(egg1);
Log.i("装饰器模式", bacon.getName() + "\t" + 
        bacon.getPrice() + "\t总价:" +
         bacon.totalPrice());

Log图(3.3):

to sum up

Cosplay:

  • Abstract structure role: Food()
  • Specific structure role: FriedRice().Noodles()
  • Abstract decorative role: GarnishFood()
  • Specific decoration role: Egg().Bacon()

The decorator mode is to decorate the original function of a class into a new thing without changing it, as well as the function of the original class, complying with the principle of opening and closing (open for extension, closed for modification)

benefit:

  • Decorator mode can bring more flexible extensions than inheritance
  • The decoration mode and the decorated person can develop independently and will not be coupled with each other.
  • The decorator mode complies with the opening and closing principle (open for extension, closed for modification)

Disadvantages:

  • Because inheritance is needed, the coupling of each class will be very high

Complete code

Go to the catalog of design patterns/design principles

Originality is not easy, your likes are your greatest support for me, leave your likes~

Guess you like

Origin blog.csdn.net/weixin_44819566/article/details/112461664