Probably the best tutorial for getting started with design patterns-Richter's substitution principle

The Liskov Substitution Principle (LSP) is an important and common one in object-oriented design (OOD). Let's summarize the knowledge points of the Liskov Substitution Principle, including:

  • Wikipedia definition
    In object-oriented programming, the Liskov Substitution principle is a special definition of subtypes. It was first proposed by Barbara Liskov in a speech entitled "Abstraction and Hierarchy of Data" at a conference in 1987.
    The content of the Liskov Substitution Principle can be described as: "Derived class (subclass) objects can replace their base class (superclass) objects in the program." The above content is not Liskov's original text, but translated from Robert Martin (Robert Martin) Interpretation of the original text. The original text is:

Barbara Liskov and Jeannette Wing published a paper in 1994 and proposed the above Liskov substitution principle.

SOLID-The L in "SOLID" refers to the Liskov Substitution Principle.
Definition 1: If for every object o1 of type T1, there is an object o2 of type T2, so that when all objects P defined by T1 are replaced with o2 by all objects o1, the behavior of the program P does not change , Then type T2 is a subtype of type T1.

Definition 2: All references to the base class must be able to transparently use the objects of its subclasses.

Liskov Substitution Principle (LSP): All references to the base class (parent class) must be able to transparently use the objects of its subclasses.

It is still a bit different from polymorphism. The Liskov Substitution Principle states that upward transformation is safe (that is, subclass objects are converted into superclass objects). Polymorphism can only be achieved under the premise of ensuring type safety.

"The Liskov Substitution Principle states that upward transformation is safe (that is, subclass objects are converted into superclass objects), and polymorphism can only be achieved under the premise of ensuring type safety." Teacher Liu said very accurately The substitution principle does include polymorphism, and a better polymorphism can be designed based on the Richter substitution principle.

Let me express my opinion. The author said that too much inverted image relies on the principle of inversion, which is oriented towards interface programming. I think the Richter ’s principle of substitution makes a clear statement of the definition of inheritance, because the six design principles are interrelated Absolutely should not be interface-oriented programming, we should explain the difference between the Richter principle and several other principles rather than commonality.

Specifically, polymorphism is an object-oriented mechanism (one of the three major features of object-oriented), which includes static polymorphism (function overloading) and dynamic polymorphism (function coverage, or dynamic binding), usually Refers to dynamic polymorphism, that is, when the program is running, the behavior (method) of the subclass object can override the behavior (method) of the parent class object. The Liskov Substitution Principle (LSP) is an object-oriented design principle. Subclass objects can be used wherever the parent class is used. This lays the foundation for the implementation of the opening and closing principle, allowing us to program against the parent class At run time, determine which subclass object to use, thereby improving the scalability and maintainability of the system. In the Liskov substitution principle, the polymorphic mechanism is actually used. When the subclass object overrides the parent class object, the behavior of the parent class can be overwritten by polymorphism.

The Liskov Substitution Principle tells us that in a software, a base class object is replaced with its subclass object, the program will not generate any errors and exceptions, and the reverse is not true. If a software entity uses a subclass object Words, then it may not necessarily be able to use base class objects. For example: I like animals, then I must like dogs, because dogs are a subclass of animals; but I like dogs, and I cannot conclude that I like animals because I do n’t like mice, although they are also animals.

For example, there are two classes, one class is BaseClass, the other is SubClass class, and SubClass class is a subclass of BaseClass class, then if a method can accept a base class object Base of type BaseClass, such as: method1 (base), Then it must accept a subclass object sub of type BaseClass, method1 (sub) can run normally. The reverse substitution does not hold. For example, a method method2 accepts the subclass object sub of the BaseClass type as the parameter: method2 (sub), then generally there can be no method2 (base) unless it is an overloaded method.

The Leeb substitution principle is one of the important ways to realize the opening and closing principle. Since the subclass objects can be used wherever the base class object is used, try to use the base class type to define the object in the program, and then re-run at runtime. Determine its subclass type and replace the parent class object with the subclass object.

Try to use the base class type to define the object in the program, and then determine its subclass type at runtime, and replace the parent class object with the subclass object

It feels like this, the convenience of the parent class has been implemented. The subclass should not be rewritten as much as possible. The subclass can implement the methods that are not implemented in the parent class?

Only rewriting virtual methods is polymorphic, and rewriting non-virtual methods has little meaning for interface-oriented programming, so understanding the Richter's principle allows us to think about interface-oriented programming ...

In JAVA, does polymorphism violate the Liskov Substitution Principle? ?
The Liskov Substitution Principle requires subclasses to avoid overriding parent class methods, but one of the conditions of polymorphism is to require subclasses to override parent class methods. Therefore, I don't understand the relationship between the Liskov Substitution Principle, inheritance, and polymorphism. Ask the great god to answer, and begin to bow down.

The original definition of LSP is more complicated. Our general interpretation of the Liskov Substitution Principle is that subclass objects can replace parent class objects, and the program logic remains unchanged. The Leeb substitution principle has at least the following two meanings:

The Leeb substitution principle is for inheritance. If inheritance is for code reuse, that is, for shared methods, then the shared parent class method should remain unchanged and cannot be redefined by the subclass. The subclass can only extend the function by adding new methods. Both the parent class and the subclass can be instantiated, and the subclass inheritance method is the same as the parent class. Where the parent class calls the method, the subclass can also call the same inheritance The logical method is the same as the parent class. When the parent class object is replaced with the subclass object, of course, the logic is consistent and there is no problem.
If the purpose of inheritance is for polymorphism, and the premise of polymorphism is that the subclass overrides and redefines the method of the parent class, in order to comply with the LSP, we should define the parent class as an abstract class, and define abstract methods to let the subclass redefine These methods, when the parent class is an abstract class, the parent class can not be instantiated, so there is no instantiable parent class object in the program. There is no possibility that the subclass replaces the parent class instance (there is no parent class instance at all) when the logic is inconsistent.
The most common situation that does not meet the LSP is that both the parent class and the child class are instantiable non-abstract classes, and the methods of the parent class are redefined by the child class. The implementation inheritance of this class will cause a difference between the parent class and the child class. Strong coupling, that is, the fact that properties and methods that are not actually related are forced together, is not conducive to program expansion and maintenance.

How to comply with LSP? To sum up a sentence-try not to inherit from the instantiable parent class, but to use inheritance based on abstract classes and interfaces.

It's very thorough. To put it bluntly, everyone is programming based on abstraction, not concrete. This can also be achieved: open to extension (based on abstraction) and prohibited from change (based on concrete).

The Liskov transformation principle requires that subclasses inherit from abstract rather than concrete inheritance. If they inherit from abstraction, subclasses must override the superclass methods. Therefore, the Richter scale principle and polymorphism are complementary! As for the first article you said, I have not heard of it.

After reading several articles just now, the author said that the Liskov transformation principle should avoid rewriting the non-abstract methods of the parent class, and the polymorphic implementation is achieved by rewriting the abstract methods, so there is no conflict.

Do not violate the polymorphism of Liskov Substitution: rewriting the abstract method of the parent class

The core idea is: the subclass must be able to replace its base class. This idea is reflected in the constraints on the inheritance mechanism. Only when the subclass can replace the base class can the system ensure that the system recognizes the subclass during runtime, which is the basis for ensuring inheritance reuse. In the specific behavior of the parent class and the child class, we must strictly grasp the relationship and characteristics in the inheritance hierarchy, and replace the base class with the child class, and the behavior of the program will not change. At the same time, this constraint is not true in the reverse, subclasses can replace the base class, but the base class does not necessarily replace the subclass.
The Liskov substitution principle mainly focuses on the foundation of abstraction and polymorphism on inheritance. Therefore, only by following the Liskov substitution principle can the inheritance reuse be ensured reliably. The implementation method is interface-oriented programming: the public part is abstracted as a base class interface or abstract class, and through Extract Abstract Class, a new method is implemented in the subclass by overriding the parent class to support the same responsibility.
The Liskov replacement principle is the design principle of the inheritance mechanism. Violation of the Liskov replacement principle will inevitably lead to violation of the open and closed principle.
The Liskov replacement principle can ensure that the system has good scalability, and at the same time implements an abstraction mechanism based on polymorphism, which can reduce code redundancy and avoid type discrimination at runtime.

Published 442 original articles · praised 1367 · 640,000 visits +

Guess you like

Origin blog.csdn.net/qq_33589510/article/details/105499367