Inheritance is a very useful concept, but it's easy to use, and it's usually better to implement it with interfaces, and the purpose of this article is to make users understand how to better use the inheritance of classes.
Inheritance is a good choice when you encounter the following situations:
(1) Simplify a low-level API function without using the class
(2) code to be reused from the base class
(3) Classes and methods that need to use the same name for different data types
(4) class level is equivalent, up to 4 to 5, and not only to increase the level of one or two
(5) Change all derived classes by changing a basic class.
1. Simplify a low-level API function that does not use the class
Class libraries make the invocation of a series of functions more reasonable, this class library is sometimes called "wrapper", especially when the functions invoked are not organized in the form of a class that is designed to simplify the API functions of drawing diagrams in forms. These class libraries, which include API functions, can generally simplify operations, but do not attempt to hide some of the basic features of API functions. There are a number of Windows Graphics API functions, but users do not need to understand some of the underlying changes. This is also the case when the user is designing the class, and the user of the class library must be considered for the underlying understanding. In fact, many class libraries are organized according to API functions, usually with two trends: making API functions more convenient for advanced users, or hiding the underlying information by a high degree of generalization, which means encapsulating the specific information of Windows API functions to the user.
But there is an implicit problem with developing class libraries, and the classes that are being packed cause a lot of text descriptions, and the more you simplify the API, the more text you need. Frequently, hundreds of API functions are organized into a dozen or 100 classes, each with dozens of or hundreds of overlapping properties, methods, and events, and sorting or browsing the class will be a very heavy task.
Design and maintain a class library that packs a variety of APIs, is a very heavy workload, imagine now to write a class library to simplify a Web service Html page generation process, this need to consider whether you need to know the "HTML", it is necessary to put these things such as "tags" or " The concept of angle brackets is implied; Is it possible to display some of these attributes, such as fonts, to the user, as long as you can process HTML, or do you need to process XML, can you call it XHTML? Wait a minute.
Suppose a base class contains a MustOverride method called parsehtml, but when XML needs to be supported, the HTML support must be replaced, and the method parsehtml be emptied, and the only option is to create a Parsexml method, However, the parsehtml method cannot be removed because when the method is removed, the HTML business is lost because the entire class is distributed and the user must have the parsehtml and Parsexml methods present, but this reduces both memory and run-time efficiency.
such as this problem exists in the network development environment, the user may have designed the HTML class library prematurely, perhaps an interface based system can better solve this problem. It allows users to create a series of HTML interfaces that can be discarded or improved when validation of XHTML or XML is a better base.
2. Code to be reused from the base class
One important reason to use inheritance is for code reuse, but this is also the most dangerous. It is because of the reuse of code, even the best designed system, sometimes there will be some designers unpredictable changes.
A classic example of high efficiency for code reuse is a data management library that now has a large application for managing several in-memory listings, and another for a list of copies from customer data that can be seen as follows:
Class CustomerInfo public
Previouscustomer as CustomerInfo public Nextcustomer as CustomerInfo public
ID as Integer public
FullName as String
' Adds a customerinfo to list
Function InsertCustomer as CustomerInfo
... .
End Function
' Removes a customerinfo the From list
Function DeleteCustomer as CustomerInfo
...
End Function
' obtains next CustomerInfo in list
Function Getnextcustmer as CustomerInfo
...
End Function
' obtains previous CustomerInfo
Function getprecustomer as CustomerInfo
...
End Function End
Class
There may also be a list of cards for a customer's purchases, as follows:
Class Shoppingcartitem
Previousitem as Shoppingcartitem
Nextitem as Shoppingcartitem
ProductCode as Integer
Function GetNextItem as Shoppingcartitem ...
End Function
...
End Class
From here, you can see the structure and pattern of the class, all have the same--insertions (insert), deletion (delete), and traversal (browse), just to operate on different data types, obviously, It is not necessary to maintain the two pieces of code that have almost the same function, and another obvious solution is to abstract the processing of the manifest into a class of its own, and then use this class to derive subclasses of different data types, such as:
Class ListItem
Previousitem as ListItem
Nextitem as ListItem
Function getnextitem as ListItem
...
End Function
...
End Class
In this case, only need to debug the ListItem class once, and the user only need to compile it once, then no longer need to manage the code on inventory management, the user only need to use it:
Class CustomerInfo
Inherits ListItem
ID as Integer
FullName As String end
class
class Shoppingcartitem
Inherits ListItem
ProductCode as Integer end
Class
3. Classes and methods that use the same name for different data types
A decision whether or not to use the inheritance method is whether there are the following issues:
(1) Whether it is necessary to perform similar operations on different data types;
(2) need not (want to) access to the program source code;
A very representative example is the software package for drawing, assuming it can draw circles, lines, and rectangles. A very simple and efficient way to do this is to use a Select Case statement that does not require inheritance, as follows:
Sub Draw (Shape as drawingshape,x as integer,y as Integer,_
Size as Integer)
Select case shape.type Case
shp Circle
' Circle drawing code, here, case,
shpline ' line,
drawing code
here, ...
End Sub
But there will be some problems with this. In the future, if you need to add the ellipse function, then you must rewrite the code, perhaps the end user does not need to access the program's source code, but may draw an ellipse requires some parameters, because the ellipse requires a long radius and a short radius. However, these parameters are not related to the parameters of other graphics, if you now want to draw a polyline (there are more than one line), you need to add some other parameters, and these parameters are independent of the parameters of other graphics.
Inheritance can solve these problems very well, a well-designed class can leave a good space for the user (MustInherit method), in which case, each shape can be satisfied, but some class properties (such as XY coordinates) can be used as the properties of the basic class, Because this attribute is required for every kind of graphic, such as:
Class Shape
Sub MustInherit Draw ()
X As Integer
Y As Integer end
class
Other graphics can inherit this class, and if you want to draw a line, the code is as follows:
Class line Extends Shape ()
Length as Integer
Sub Overrides Draw
' implement Draw-end Sub-end
Cla SS-
Rectangular classes should also be represented as follows:
class Rectangle Extends line ()
Width as Integer
Sub Overrides Draw ()
' Implement Draw here-end Sub-end
Class
Its inheriting subclasses (for example, rectangles) can inherit from the binary file of the image class, rather than on the basis of the code of the underlying class.
4. The methods of the base class need to be changed
Visual Basic (and others that provide an inherited programming language) makes it possible for users to overload the basic class method, as long as the methods of the base class that can be accessed in the derived class can be loaded (except those notinheritable). If the user feels that the DisplayError method of the basic class needs to give an error number, not just a description of the error, the user can change the behavior of the method in the derived class, then the derived class will call its own method, not the base class method.
5. By changing a basic class, all derived classes are changed
A powerful function of inheritance is that when you change the properties of a basic class, changes the corresponding structure of all derived classes, but this is also a risky behavior-it is possible to change the base class that you design, and the derived classes that others derive from the base class will produce errors.