Seven principles of design pattern -- Demeter's law

Posted by anler on Tue, 25 Jan 2022 12:19:52 +0100

Basic introduction:

  1. One object should have minimal knowledge of other objects
  2. The closer the relationship between classes, the greater the degree of coupling
  3. Dimitri's law is also called the least known principle, that is, the less a class knows about the class it depends on, the better. In other words, no matter how complex the dependent class is, try to encapsulate the logic inside the class. In addition to providing public methods, it will not disclose any information
  4. There is also a simple definition of Dimitri's Law: only communicate with direct friends
  5. Direct friend: each object is coupled with other objects. As long as there is a coupling relationship between two objects, we say that the two objects are friends. There are many ways of coupling, such as dependency, association, combination, aggregation and so on. Among them, we call the classes that appear in member variables, method parameters and method return values as direct friends, while the classes that appear in local variables are not direct friends. That is, unfamiliar classes should not appear inside the class in the form of local variables.
There is a school with subordinate colleges and headquarters. Now it is required to print out the ID of the staff of the school headquarters and the ID of the staff of the college

Actions against Dimitri's Law:

Employee class:
//School headquarters staff
public class Employee {
    private String id;

    public Employee() {
    }
    public Employee(String id) {
        this.id = id;
    }

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }
}
CollegeEmoloyee class:
//College staff
public class CollegeEmoloyee {
    private String id;
    public CollegeEmoloyee() {
    }

    public CollegeEmoloyee(String id) {
        this.id = id;
    }

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }
}

collegeManger class:

public class CollegeManger {
    public List<Employee> getAllEmployee(){
        List<Employee> employees = new ArrayList<>();
        for (int i = 0; i < 10; i++) {
            Employee employee = new Employee();
            employee.setId("staff id:" + i);
            employees.add(employee);
        }
        return employees;
    }

}

SchoolMange class:

//Analyze SchoolManger's direct friends
//CollegeEmoloyee,CollegeManger

//Employee: it's not a direct friend, but a stranger. Doing so violates Dimitri's Law (it appears in the form of local variables)
public class SchoolManger {
    public List<CollegeEmoloyee> getAllEmoloyee(){
        List<CollegeEmoloyee> collegeEmoloyees = new ArrayList<>();
        for (int i = 0; i < 5; i++) {
            CollegeEmoloyee collegeEmoloyee = new CollegeEmoloyee();
            collegeEmoloyee.setId("staff id:"+i);
            collegeEmoloyees.add(collegeEmoloyee);
        }
        return collegeEmoloyees;
    }
    void print(CollegeManger sub){
        System.out.println("=========School headquarters staff============");
        //Analyze problems
        //1. The Employee here is not a direct friend of SchoolManger
        //2.Employee appears in SchoolManger as a local variable
        //3. Violation of Dimitri's law
        List<Employee> employee = sub.getAllEmployee();
        for (Employee e:employee
        ) {
            System.out.println(e.getId());
        }
        System.out.println("=========Branch employees============");
        List<CollegeEmoloyee> collegeEmoloyees = this.getAllEmoloyee();
        for (CollegeEmoloyee c:collegeEmoloyees
             ) {
            System.out.println(c.getId());
        }

    }
}

Main category:

    public static void main(String[] args) {
        SchoolManger schoolManger = new SchoolManger();
        schoolManger.print(new CollegeManger());
    }
//Analyze SchoolManger's direct friends
//CollegeEmoloyee,CollegeManger
 //Employee: it's not a direct friend, but a stranger. Doing so violates Dimitri's Law (it appears in the form of local variables)
//Analyze problems
 //1. The Employee here is not a direct friend of SchoolManger
 //2.Employee appears in SchoolManger as a local variable
 //3. Violation of Dimitri's law

How to improve???

1. The problem with the previous design is that in the SchoolManager, the Employee class is not a direct of the SchoolManger class
  Friends (analysis)
2. According to Demeter's law, we should avoid the coupling of such indirect friends in the class
 3. Encapsulate the method of outputting college employees into CollegeMage

Chief staff:

public class zongyuangong {
    private String id;

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }
}

Branch staff:

public class fenyuangong {
    private String id;

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }
}

Add employee class:

public class tianjiafeng {
    public List<fenyuangong> addyuangong(){
        ArrayList<fenyuangong> fenyuangongArrayList = new ArrayList<>();
        for (int i = 0; i < 5; i++) {
            fenyuangong fenyuangong = new fenyuangong();
            fenyuangong.setId("staff id:"+i);
            fenyuangongArrayList.add(fenyuangong);
        }
        return fenyuangongArrayList;
    }
    public void print(){
        List<fenyuangong> addyuangong = this.addyuangong();
        for (fenyuangong f:addyuangong
             ) {
            System.out.println(f.getId());
        }
    }
}

Add the chief staff category:

public class tianjiazong {
    public List<zongyuangong> addyuangong(){
        ArrayList<zongyuangong> zongyuangongArrayList = new ArrayList<>();
        for (int i = 0; i < 10; i++) {
            zongyuangong zongyuangong = new zongyuangong();
            zongyuangong.setId("staff id:"+i);
            zongyuangongArrayList.add(zongyuangong);
        }
        return zongyuangongArrayList;
    }
    public void println(tianjiafeng fenyuangong){
        System.out.println("========Chief staff id===========");
        List<zongyuangong> addyuangong = this.addyuangong();
        for (zongyuangong z:addyuangong
             ) {
            System.out.println(z.getId());
        }
        System.out.println("========Branch staff id===========");
        fenyuangong.print();
    }

}

Main category:

public class Demter {
    public static void main(String[] args) {
        tianjiazong zongyuangong = new tianjiazong();
        zongyuangong.println(new tianjiafeng());

    }
}

Topics: Design Pattern