Demeter principle, Open and close principle, composite reuse principle – the combination of text code understanding
- What are the seven design principles?
- Why use seven design principles?
- Demeter principle
- The open closed principle
- Principle of composite reuse
- Core ideas of design principles
- Summary of design patterns:
What are the seven design principles?
- Single responsibility principle
- Interface Isolation Principle
- Rely on the inversion principle
- Richter’s substitution principle
- The open closed principle
- Demeter’s rule
- Principle of composite reuse
The first six are generally understood and there is no synthetic reuse principle
Why use seven design principles?
- Code reuse (you don’t have to write the same code more than once);
- Readability (normative programming that is easy for other programmers to read and understand);
- Extensibility (also called maintainability when new features need to be added);
- Reliability (when we add new features, there is no impact on the original features);
- The program presents high cohesion, low coupling and other characteristics
Demeter principle
Demeter principle definition:
- One object should have minimal knowledge of other objects
- The closer the relationship between classes, the greater the degree of coupling
- There’s a simpler definition of Demeter’s rule: Only communicate with your immediate friends
Demeter’s law is also called the least known principle, that is, a class knows as little as possible about the class it depends on. That is, no matter how complex the dependent class is, it tries its best to encapsulate logic inside the class and provide public methods to the public without disclosing information to the public
What is a direct friend?
In a class: global variables, return values, parameter passing are called direct friends,
Local variables are called strange friends
Let’s take a look at some easy-to-understand code:
public class A {}
public class B {}
public class C {}
public class D {}
public class E {}
public class B {
public A mA;
public C getC(a){
return null;
}
public void showD(a){
D d = new D();
}
public void setA(E e){}}Copy the code
In category B:
- public A mA; The global variable
- Public C getC(){return value return null; }
- Public void showD(){D D = new D(); }
- Public void setA(E E){} Parameter pass
A,C,E are B’s immediate friends and D is B’s strange friend
Not following the Demeter principle code:
public class Student{
String name = "";
public Student(String name) {
this.name = name; }}public class StudentManager {
public void getStudentNumber(Student student){
ArrayList<String> list = new ArrayList<>();
for (int i = 0; i < 10; i++) {
list.add(student.name+i);
Log.i("dimiter:"."Now it's number one."+i+"A student named:"+list.get(i));
}
Log.i("dimiter:".There's a total of+list.size()+"A student"); }}// Use code:
// Demeter principle
StudentManager studentManager = new StudentManager();
studentManager.getStudentNumber(new Student("Zhang"));
Copy the code
Analysis:
- The Student class has the NEME parameter (Student name)
- The StudentManager class creates 10 students and prints their names
Code for violation of Demeter principle:
The code in figure (1.1) :
\
Why the Demeter principle is violated:
Demeter’s principle, also known as the least know principle, begins with understanding:
- What is theLeast know principle, which means that the coupling between two classes is very low, and the low coupling means that there is very little interaction between them, i.eThe less a class knows about the classes it depends on, the betterIn the
The code in figure (1.1)
As you can see in this example, the StudentManager() class creates 10 student names for the Studnet() class. Too much - Don’t disclose information:
The code in figure (1.1)
The code in the red box should be done inside Student() and then called directly by StudentManager()
StudentManager() needs to count all students. StudentManager() needs to count all students. StudentManager() needs to count all students Give me what I ask you for, don’t let me calculate (the less a class knows about its dependent classes, the better), and don’t let me know about your stuff (don’t divulge information).
Again, take a look at the code that follows the Demeter principle and you’ll see
Follow the Demeter Principle:
public class Student{
String name = "";/// Student name
/// use this to store all student names
ArrayList<String> mList = new ArrayList<>();
public Student(String name) {
this.name = name;
}
Create 10 students according to the Demeter principle
public List<String> newStudentName(a){
for (int i = 0; i < 10; i++) {
mList.add(name+i);
Log.i("dimiter:"."Now it's number one."+i+"A student named:"+mList.get(i));
}
returnmList; }}public class StudentManager {
public void getStudentNumber(Student student) {
/// Follow the Demeter principle
List<String> list = student.newStudentName();
Log.i("dimiter:".There's a total of + list.size() + "A student"); }}// Use code:
// Demeter principle
StudentManager studentManager = new StudentManager();
studentManager.getStudentNumber(new Student("Zhang"));
Copy the code
Student() creates 10 students and gives them to StudentManager() :
The least known (Demeter) principle is that a class knows as little as possible about the classes it depends on and does not divulge information,
One object should have minimal knowledge of other objects
A minimum of 10 students
All I know is that you have 10 students, and how did you get those 10 students
Rendering (2.1) :
The open closed principle
Definition of open and close principle:
- The open and close principle is the most basic and important design principle in programming
- A software entity such as classes, modules, and methods should be open to extension (to providers) and closed to modification (to users), build the framework with abstractions, and extend the details with implementations (details refer to implementing code).
- When software requirements change, try to achieve the change by extending the behavior of the software entity rather than by modifying existing code
- The purpose of following other principles and using design patterns is to follow the open closed principle
Not following the open and close principle code:
// Shape type
public abstract class Shape {
Rectangle */ Rectangle */
int type;
}
/ / round
public class Circular extends Shape {
public Circular(a) {
type = 1; }}/ / rectangle
public class Rectangle extends Shape {
public Rectangle(a) {
type = 2; }}// Open/close principle Manager class
public class OpenManager {
public void showShape(Shape shape){
if (shape .type == 1) {
drawCircular(shape);
}else if (shape.type == 2){ drawRectangle(); }}private void drawRectangle(a) {
Log.i("Open"."Create rectangle");
}
private void drawCircular(Shape shape) {
Log.i("Open"."Create a circle"); }}// Use code:
// Open close principle
OpenManager openManager = new OpenManager();
openManager.showShape(new Circular());/ / create a circle
openManager.showShape(new Rectangle());// Create rectangle
Copy the code
Rendering (2.2) :
Why not follow the open close principle:
The key definition of the open close principle is:
Extend open (to providers), close (to users), build frameworks with abstractions, extend details with implementations (details refer to implementation code)
Now if I wanted to add a new triangle what would I do?
Is it written like this?
public class Triangle extends Shape{
public Triangle(a) {
type = 3; }}public class OpenManager {
public void showShape(Shape shape){
if (shape .type == 1) {
drawCircular();/ / create a circle
}else if (shape.type == 2){
drawRectangle();// Create rectangle
}else if(shape.type == 3){
drawTriangle();// Create a triangle}}private void drawTriangle(a) {
Log.i("Open"."Create a triangle"); }}// Use the code
// Open close principle
OpenManager openManager = new OpenManager();
openManager.showShape(new Circular());
openManager.showShape(new Rectangle());
openManager.showShape(new Triangle());
Copy the code
Rendering (2.3) :
\
Not only does this result in code conflicts during the process of modification, but also through if else judgment
What if I have 100 shapes? A hundred times?
If lese if lese if lese if lese if lese if lese… ?
This writing error rate is too high, and does not comply with the extension open, modify closed
Follow the open and close principle code:
public abstract class Shape {
public abstract void showShape(a);
}
public class Circular extends Shape {
@Override
public void showShape(a) {
Log.i("Open"."Create a circle"); }}public class Triangle extends Shape{
@Override
public void showShape(a) {
Log.i("Open"."Create a triangle"); }}public class Rectangle extends Shape {
@Override
public void showShape(a) {
Log.i("Open"."Create rectangle"); }}public class OpenManager {
public void showShape(Shape shape){
// Follow the open/close principleshape.showShape(); }}// Use code:
// Open close principle
OpenManager openManager = new OpenManager();
openManager.showShape(new Circular());
openManager.showShape(new Rectangle());
openManager.showShape(new Triangle());
Copy the code
Analysis:
- As you can see, even if we add a Triangle class, we can draw it from Shape, and we don’t need if else
- This is really for extension development, but for modification, even if I’m adding an oval now, I need to inherit Shape() and output it
public class Ellipse extends Shape{
@Override
public void showShape(a) {
Log.i("Open"."I'm a newly created oval."); }}// Open close principle
OpenManager openManager = new OpenManager();
openManager.showShape(new Circular());
openManager.showShape(new Rectangle());
openManager.showShape(new Triangle());
openManager.showShape(new Ellipse());// Create an ellipse
Copy the code
This is similar to the dependency inversion principle, except that the dependency inversion principle is implemented through interfaces and the open and close principle is implemented through abstractions.
Principle of composite reuse
Synthetic reuse principle definition:
When software reuse, it is necessary to use association relation such as combination or aggregation first, and then inheritance relation
Generally, class reuse is divided into inheritance reuse and composite reuse. Although inheritance reuse has the advantages of simplicity and easy implementation, it also has the following disadvantages:
- Inheritance reuse breaks class encapsulation. Because inheritance exposes the implementation details of the parent class to the child class, the parent class is transparent to the child class, so this reuse is also known as “white box” reuse.
- A subclass has a high degree of coupling with its parent. Any change in the implementation of the parent class results in a change in the implementation of the subclass, which is not conducive to the extension and maintenance of the class.
- It limits the flexibility of reuse. An implementation inherited from a parent class is static and defined at compile time, so it cannot be changed at run time
Try not to inherit. If it does, the subclass is highly coupled to the parent class, which is transparent to the subclass. It is not good for maintenance. If you must reuse it, you can use combination/aggregation.
It doesn’t matter if you don’t know about composition/aggregation, I’ll go into more detail about relationships between classes in the next chapter!
Core ideas of design principles
- Identify changes that may need to be made to your application and isolate them from code that doesn’t need to be changed.
- Program to the interface, not to the implementation.
- Strive for loose coupling design between interacting objects.
- Extend open (to providers), close (to users), build frameworks with abstractions, extend details with implementations (details refer to implementation code)
Demeter (least known) principle code
The open closed principle
Summary of design patterns:
- Open and close (OCP) principle: expand open, modify closed
- Interface isolation principle: Dependencies between classes should be established on the smallest interface
- Single responsibility principle: one class is responsible for one responsibility, not one class for one responsibility
- Dependency inversion principle: Interface oriented programming
- Richter’s substitution principle: when inheriting, try not to rewrite the method of the parent class in the subclass, if must use, can use aggregation, composition, dependency to solve the problem, do not modify the method of the parent class!
- The Demeter (least know) rule: Communicate only with immediate friends, and a class knows as little as possible about the classes it depends on
- The rule of composite reuse: use composite or aggregate relationships as much as possible, and consider inheritance second
What do you like?
- The Seven Java Design Principles of a Single responsibility, interface Isolation principle (Literal code combined understanding)
- Dependency Inversion, Richter’s Substitution principle
- Android Studio UML modeling
Go to the Design Patterns/Design Principles directory page
Original is not easy, remember to like oh ~