UML class diagrams in UML, object-oriented principles and method reuse-java articles

UML class diagrams are structural diagrams and are often used to describe the static structure of a system. A UML class diagram usually includes a UML diagram of a class, a UML diagram of an interface, a UML diagram of a generalization relationship, a UML diagram of an association relationship, a UML diagram of a dependency relationship, and a UML diagram of a realization relationship.

Class UML Diagram

In the UML diagram of a class, a rectangle is used to describe the main composition of a class, and the rectangle is vertically divided into three layers.
       

The first layer is the name layer . If the class name is a regular font, it indicates that the class is a concrete class; if the class name is an italic font , it indicates that the class is an abstract class .
The second layer is the variable layer, also known as the attribute layer , which lists the member variables and types of the class . The format is " variable name: type ". When expressing a class in UML, only the most important member variables can be listed according to the needs of the design. name.

If the access permission of the variable is public , you need to modify it with a "+" symbol in front of the variable name ;

If the access permission of the variable is protected , you need to use the "#" symbol in front of the variable name ;

If the access permission of the variable is private, you need to modify it with a "-" symbol in front of the variable name ;

If the access rights of the variable are friendly , no symbols are used in front of the variable name.


The third layer is the method layer, also known as the operation layer , which lists the methods and return types of the class. The format is "method name (parameter list): type"

When using UML classes, only the most important methods can be listed according to the design needs.

If the access permission of the method is public , it needs to be modified with a "+" sign before the name of the method;

The access permission of the method is protected  , decorated with "#" symbol;

The access right of the method is private, decorated with "-" symbol;

If the access rights of the method are friendly , no symbols are used in front of the method name.

If the method is a static method , underline the method name.

A UML diagram representing an interface

Use a rectangle to describe the main composition of an interface, divided into 3 layers.
The first layer is the name layer. The name of the interface must be in italics , and the name should be modified with <<interface>> .
The second layer is the constant layer , which lists the constants and types in the interface , and the format is " constant name: type ".

The access rights of the constants in the interface are public, and the constant name is decorated with a "+" symbol .
The third layer is the method layer, also known as the operation layer , which lists the methods and return types in the interface , and the format is " method name (parameter list): type ". The access rights of the methods in the interface are public, and the "+" symbol is used to modify the method name .

generalization relationship

Generalization refers to the inheritance relationship of classes. If a class is a subclass of another class, UML represents the inheritance relationship between the two classes by connecting the UML diagrams of the two classes with a solid line starting from the UML diagram of the subclass and ending at the UML diagram of the subclass. A UML diagram of the parent class, but with a hollow triangle at the endpoint to indicate the end of the solid line.

Example: UML diagram of the Animal class and its two subclasses Dog and Cat

 

connection relation

If the member variable in class A is a variable declared by class B (interface), then the relationship between A and B is an association, which means that A is associated with B. If A is related to B, then UML connects the UML diagrams of A and B by using a solid line starting from the UML diagram of A and ending with the UML diagram of B, but using a UML diagram pointing to B at the end A directional arrow indicates the end of the solid line.

For example: UML diagram of ClassRoom class associated with Light class.

 

dependencies 

 If the parameters of a method in class A are variables declared with class B (interface) or the data type returned by a method is type B, then the relationship between A and B is a dependency relationship, and A depends on B. If A depends on B, UML connects the UML diagrams of A and B by using a dotted line. The starting end of the dotted line is the UML diagram of A, and the ending point of the dotted line is the UML diagram of B, but the end point uses a directional arrow pointing to the UML diagram of B. Indicates the end of a dashed line.

ClassRoom depends on the UML diagram of the Student interface

 When it is necessary to emphasize that A is dependent on B through method parameters, use a dashed line in the UML diagram to connect A and B in the UML diagram

achieve relationship

If a class implements an interface, then the relationship between the class and the interface is Realization, which is called the class implements the interface . UML uses a dotted line to connect a class and the interface it implements. The start end of the dotted line is the class, and the end end of the dotted line is the interface it implements, but the end end uses a hollow triangle to indicate the end of the dotted line.

UML diagram of ClassOne and ClassTwo classes implementing Create interface

 Notes:

UML uses annotations (Annotation) to provide additional instructions for class diagrams. UML displays the given annotation in a curled rectangle and uses dashed lines to connect the curled rectangle to the entity it annotates .

Example: A UML diagram of the Computer class that uses annotations for the add() method in the Computer class

 

object-oriented principles

Abstract classes and interfaces


Abstract (abstract) classes have the following characteristics:
(1) Abstract classes can have abstract methods or non-abstract methods.
(2) Abstract classes cannot use the new operator to create objects.
(3) If a non-abstract class is a subclass of an abstract class, it must override the abstract method of the parent class 

(4) Make up -transition objects : Although an abstract class cannot use the new operator to create objects, its non-abstract subclasses must rewrite all of its abstract methods, allowing the objects declared by an abstract class to become up-transition objects of its subclasses object, and calls methods overridden by the class.

For example: there is an abstract method add(int x, int y) in abstract class A

A.java


public abstract class A {
	public abstract int add(int x,int y);
}

B.java

public class B extends A{
	public int add(int x,int y) {
		return x+y;
	}

}

Application.java

public class Application {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		A a;
		a = new B(); //a是B类对象的上转型对象
		int m = a.add(3, 2);//a调用子类B重写的add()方法
		System.out.println(m);
		
	}

}

interface

The interface has the following characteristics:

(1) Abstract method, default method and static method with public permission in the interface

(2) The interface is implemented by the class, and a class implements an interface, then it must rewrite the abstract method in the interface.

(3) Interface callback: Interface callback refers to assigning the reference of the object of the class that implements the interface to the interface variable declared by the interface, then the interface variable can call the interface method rewritten by the class.

There is an abstract method sub(int x, int y) in the following interface Com;

Com.java

public interface Com {
	public abstract int sub(int x,int y);
}

ComImp.java

 class ComImp implements Com {
	public int sub(int x,int y) {
		return x-y;
	}
}

Application.java

public class Application {
	public static void main(String args[]) {
		Com com;
		com = new ComImp();//com变量存放ComImp类的对象的引用
		int m = com.sub(8,2); //com回调ComImp类实现的接口方法
		System.out.println(m); //输出结果为6
	}

}

Output result: 6

Abstract Oriented Programming

When designing a class, let this class face the abstract class or interface class, that is, the important data in the class are variables declared by the abstract class or interface class.

For example: There is already a Circle class, and the object circle created by this class calls the getArea() method to calculate the area of ​​the circle.

public class Circle {
	double r;
	Circle(double r){
		this.r = r;
	}
	public double getArea() {
		return(3.14*r*r);
	}

}
public class Pillar {
	double height;
	 Circle bottom; //将Circle对象作为成员,bottom是用具体类Circle声明的变量
	Pillar(Circle bottom,double height){
		this.bottom = bottom;
		this.height = height;
	}
	public double getVolume() {
		return bottom.getArea()*height;
	}
}

In the above Pillar class, bottom is a variable declared with the concrete class Circle. If it does not involve changes in user requirements, there is nothing wrong with the design of the above Pillar class, but the user hopes that the Pillar class can create a cylinder with a triangular bottom. The above-mentioned Pillar class cannot create such a column, that is, the above-mentioned designed Pillar class cannot meet the needs of users.


Redesign the Pillar class. First of all, note that the key to calculating the volume of a cylinder is to calculate the area of ​​the base. When calculating the area of ​​the base of a cylinder, one should not care about the specific shape of its base, but only whether the figure has a method for calculating the area. Therefore, when designing the Pillar class, it should not let its bottom be a variable declared by a specific class.


Next, we will redesign the Pillar class for abstraction. First write an abstract class Geometry (or interface), which defines an abstract getArea() method.

public abstract class Geometry { //如果使用接口,需用interface来定义Geometry
	public abstract double getArea();
}

Now the Pillar class can write code for the Geometry class, that is, the Pillar class should use the Geometry object as its own member, and this member can call the getArea() method rewritten by the Geometry subclass

The design of the Pillar class no longer depends on the concrete class, but is oriented to the Geometry class, that is, the bottom in the Pillar class is a variable declared with the abstract class Geometry, not a variable declared by the concrete class.

public class Pillar {
	double height;
	 Geometry bottom; //将Circle对象作为成员,bottom是用具体类Circle声明的变量
	Pillar(Geometry bottom,double height){
		this.bottom = bottom;
		this.height = height;
	}
	public double getVolume() {
		return bottom.getArea()*height; //bottom可以调用子类重写的getArea方法
	}
}
public class Retangle extends Geometry{
	double a,b;
	Retangle(double a,double b){
		this.a = a;
		this.b = b;
	}
	public double getArea() {
		return a*b;
	}
}
public class Circle extends Geometry {
	double r;
	Circle(double r){
		this.r = r;
	}
	public double getArea() {
		return(3.14*r*r);
	}

}
public class Application {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Pillar pillar;
		Geometry bottom;
		bottom = new Retangle(22,100);
		pillar = new Pillar(bottom,58);
		System.out.println("矩形底体积:"+pillar.getVolume());
		
		bottom = new Circle(10);
		pillar = new Pillar(bottom,60); //pillar是具有圆形底的柱体
		System.out.println("圆形底的体积:"+pillar.getVolume());
	}

}

operation result:

Volume of rectangular base: 127600.0
Volume of circular base: 18840.0

By designing the Pillar class for abstraction, the Pillar class no longer depends on the concrete class. , whenever the system adds a new Geometry subclass, such as adding a Triangle subclass, you can use Pillar to create a cylinder with a triangular base without modifying any code of the Pillar class

"Open-Closed" Principle

The so-called "Open-Closed Principle" (Open-Closed Principle) is to make the user's design "open to extension and closed to modification".
Essence means that when adding new modules to a design, existing modules do not need to be modified. When giving a design, the change of user needs should be considered first, and the part that responds to user changes should be designed to be open to expansion, while the core part of the design is the basic structure determined after careful consideration, and this part should be closed to modification Yes, that is, it cannot be changed due to changes in user needs.

For example, there are 4 class UML class diagrams as shown in the figure


The Geometry class and Pillar class in this design are the closed parts of the system for modification, while the subclasses of Geometry are the open parts for extension. When adding any Geometry subclass to the system (open to extension), you can use Pillar to create a column with a specified base of the new Geometry subclass without modifying the Pillar class.
 

Two techniques for method reuse: class inheritance and object composition

The subclass inherits the method of the parent class as one of its own methods, which can be called by any instance method declared in the subclass .

The method of the parent class can be reused by the subclass in the way of inheritance.
The advantage of reusing parent class methods through inheritance is that subclasses can override parent class methods, that is, it is easy to modify or extend those reused
methods.


The disadvantages of reusing methods through inheritance are as follows:
(1) The method inherited by the subclass from the parent class is determined at compile time, so the behavior of the method inherited from the parent class cannot be changed during runtime.
(2) The relationship between the subclass and the parent class is a strong coupling relationship . When the behavior of the method of the parent class changes, it will inevitably lead to
changes in the subclass.
(3) Reuse through inheritance is also called "white box" reuse . The disadvantage is that the internal details of the parent class are visible to the subclass.

Combined multiplexing

A class can use objects as its own member variables. If you use such a class to create an object, then there will be other objects in the object, and the object will use other objects as its own components (this is what people often say Has-A) , or the object is composed of several objects.
If an object a combines object b, then object a can delegate object b to call its method, that is, object a reuses the method of object b in a combined manner.


The advantages of reusing methods by combining objects
are: (1) Reusing methods by combining objects is also called "black box" reuse, because the current object can only entrust the contained objects to call its methods, and the objects contained in the current object The details of the method are not visible to the current object.
(2) The object and the contained objects belong to the weak coupling relationship , because if the code of the class of the object contained in the current object is modified, it is not necessary to modify the code of the class of the current object.
(3) The current object can dynamically specify the contained objects at runtime , such as the bottom object of the Pillar combination, and the bottom can be specified as a Circle object or a Rectangle object at runtime.
 

The following simulates the dynamic replacement of drivers in cars

person.java

public abstract class Person {
	public abstract String getMess();
}

 Car.java

public class Car {
	Person person; //组合驾驶员
	public void setPerson(Person p) {
		person = p;
	}
	public void show() {
		if(person == null) {
			System.out.println("没人驾驶");
		}
		else {
			System.out.println("驾驶人是:");
			System.out.println(person.getMess());
		}
	}
}

MainClass.java

public class MainClass {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Car car = new Car();
		int i=1;
		while(true) {
			try {
				car.show();
				Thread.sleep(2000); //每个2000毫秒更换驾驶员
				Class<?>cs = Class.forName("Driver"+i); 
				Person p = (Person)cs.getDeclaredConstructor().newInstance(); //无人驾驶或当期驾驶员继续驾驶
				car.setPerson(p); //更换驾驶员
				i++;
			}catch(Exception exp) {
				i++;
			}
			if(i>10) i=1;
		}
	}

}

Continue to edit the Person class subclass program, the subclass name must be Drive1, Drive2. . . .

public class Driver1 extends Person{
	public String getMess() {
		return "我是美国驾驶员";
	}
}
public class Driver5 extends Person {
	public String getMess() {
		return "我是女驾驶员";
	}
}

operation result:

No one is driving
The driver is:
I am a US driver
The driver is:
I am a US driver
The driver is:
. . . .

Guess you like

Origin blog.csdn.net/m0_46965984/article/details/124446386