Welcome to follow the official wechat account: FSA Full Stack Action 👋

I. Introduction to combination pattern

The combination mode is also called the partial whole mode, which combines the objects into a tree structure to represent the “partial – whole” hierarchy, which can better realize the management operation; The composite pattern allows users to manipulate individual and composite objects in a consistent way; The basic operations for partial-whole objects are mostly the same, but there are some differences.

Essence: Composite patterns can be represented using a tree

  • The core of

    • Object declaration interfaces in a composition (Component) : Where appropriate, implement the default behavior of interfaces shared by all classes. Declare an interface for accessing and managing Component children.
    • Container object (Composite) : defines a Component behavior that stores sub-components and implements operations such as adding and deleting sub-components in the Component interface.
    • Leaf object: No child nodes.

    Note: Both container objects and leaf nodes implement the Component interface, which is the key to treating them the same.

  • Application scenarios

    • The head office of the bank, the head office has front desk, logistics, network departments, etc., under the jurisdiction of the local branches, there are also front desk, logistics, network departments, the smallest branch is no sub-branch
    • Companies, too, have subsidiaries under the head office, and most of the departments in each company are similar
    • Folders and files are also hierarchically managed
  • When to use

    • When you want to express a partial-whole hierarchy of objects
    • It provides a consistent way to manipulate nodes and leaves on a tree, regardless of whether it is a node or leaf, when the object we are dealing with can generate a tree structure
  • advantages

    • The customer only needs to face consistent objects without considering the whole part or node leaves
    • Easy to create complex hierarchies
  • disadvantages

    • The client needs to spend more time sorting out the hierarchy between classes

Two, combination pattern code implementation

Take “file-folder” as an example. In Linux, both are files and define a file interface:

Note: The Component interface defines some common properties and methods (and can add some default behavior), so use abstract classes. In addition to the display() method, you can also define methods such as rename(), delete() and other methods that are available to files and folders. Of course, these methods are different for files and folders. The delete() of a folder can delete the entire file directory.

/** * Declare an interface for accessing and managing sub-components@author GitLqr
 */
public abstract class File {

	String name;

	public File(String name) {
		this.name = name;
	}

	public String getName(a) {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	/** * Display subcomponent information */
	public abstract void display(a);
}
Copy the code

Define a container object (folder) class:

Description: because it is a container object, need to define the container (usually an array) to store the sub-parts, and add the necessary methods to manage the sub-parts, such as: add, delete.

/** * Container object (defines the behavior of the branch, stores the sub-parts) : folder **@author GitLqr
 */
public class Folder extends File {

	private List<File> files = new ArrayList<>();

	public Folder(String name) {
		super(name);
	}

	/** * Browse files in folders */
	@Override
	public void display(a) {
		for(File file : files) { file.display(); }}/** * Add files */ to the folder
	public void addFile(File file) {
		files.add(file);
	}

	/** * Delete files from folders */
	public void removeFile(File file) { files.remove(file); }}Copy the code

Define leaf object (concrete file) classes:

Note: Leaf objects have no child nodes, so you don’t need to implement the methods in the Component interface like folders.

/** * Leaf node: text file **@author GitLqr
 */
public class TextFile extends File {

	public TextFile(String name) {
		super(name);
	}

	@Override
	public void display(a) {
		System.out.println("Text file - File name:"+ name); }}/** * Leaf node: image file **@author GitLqr
 */
public class ImageFile extends File {

	public ImageFile(String name) {
		super(name);
	}

	@Override
	public void display(a) {
		System.out.println("Image file name:"+ name); }}Copy the code

Use:

Note: The display() method displays information about all “files” in the container for the folder [container object], and displays information about itself for the specific file [leaf object].

public static void main(String[] args) {
    Folder folder1 = new Folder("Folder 1");

    // Fill folder 2
    Folder folder2 = new Folder("Folder 2");
    TextFile readmeFile = new TextFile("readme.txt");
    ImageFile qrcodeFile = new ImageFile("qrcode.jpg");
    ImageFile pictureFile = new ImageFile("picture.jpg");
    folder2.addFile(readmeFile);
    folder2.addFile(qrcodeFile);
    folder2.addFile(pictureFile);

    // Add folder 2 to folder 1
    folder1.addFile(folder2);
    // "recursively" traverses all files in folder 1
    folder1.display();
}
Copy the code

If this article has been helpful to you, please feel free to follow my wechat official account: FSA Full Stack Action, which will be the biggest incentive for me. The public account not only has Android technology, iOS, Python and other articles, there may be skills you want to know oh ~