里氏替换原则
1.定义
子类可以实现父类的抽象方法,但不能覆盖父类的非抽象方法。
子类中可以增加自己特有的方法
1.2 UML类图
1.3 设计背景
有时候父类有多个子类,但在这些子类中有一个特例,如果不遵循里氏替换原则,重写了父类的方法,虽然实现了功能,会整个继承体系的可复用性会比较差,比如B继承了A,B重写了A的fun1()方法,C又继承了B,这个时候C使用fun1()方法,但使用的确是B的fun1(),而不是A的fun1()方法。按照继承设计的作用,子类是可以继承父类的方法和成员,减小代码冗余,增加复用。但是因为重写导致了复用性降低,C本来是想使用到A的fun1()方法,但是确没有使用到。
public class A
{
void fun1(int a, int b)
{
int result = a-b;
System.out.println(a + " - " + b + " = " + result);
}
}
public class B extends A
{
/**
* 子类重写了父类的fun1方法
*/
void fun1(int a, int b)
{
int result = a+b;
System.out.println(a + " + " + b + " = " + result);
}
void fun2(int a, int b)
{
int result = a*b;
System.out.println(a + " * " + b + " = " + result);
}
}
public class C extends B
{
void fun3(int a, int b)
{
int result = a/b;
System.out.println(a + " / " + b + " = " + result);
}
}
public class Test
{
public static void main(String[] args)
{
A a = new A();
a.fun1(12, 4); //12 - 4 = 8
B b = new B();
b.fun1(12, 4);//12 + 4 = 16
C c = new C();
c.fun1(12, 4);//12 + 4 = 16
A ab = new B();
ab.fun1(12, 5);//12 + 5 = 17 运行时多态
}
}
1.4 实现思路
如果既想满足里氏替换原则,又想满足这个子类的功能时,可以在子类中可以增加自己特有的方法fun2,当然也可以不走继承,使用关联,聚合,组合来解决问题。
1.5 实现场景
public class A
{
public void fun1(int a, int b)
{
int result = a-b;
System.out.println(a + " - " + b + " = " + result);
}
}
public class A1
{
public void fun1(int a, int b)
{
A aObject = new A();//使用依赖关系 让A1可以使用A的方法
aObject.fun1(a,b);
}
public void fun2(int a, int b)
{
int result = a+b;
System.out.println(a + " + " + b + " = " + result);
}
}
public class B extends A
{
/**
* @param a
* @param b
* 增加加自己特有的方法fun2
*/
public void fun2(int a, int b)
{
int result = a+b;
System.out.println(a + " + " + b + " = " + result);
}
}
public class Test
{
public static void main(String[] args)
{
A a = new A();
a.fun1(12, 4); //12 - 4 = 8
B b = new B();
b.fun1(12, 4);//12 - 4 = 8
b.fun2(12, 4);//12 + 4 = 16
A1 a1 = new A1();
a1.fun1(12, 4);//12 - 4 = 8
a1.fun2(12, 4);//12 + 4 = 16
}
}