**
面向对象-----继承
**
继承:就是把多个事务的共性部分向上抽取到父类当中,父类的成员,子类可以继承使用,继承可以提高代码的复用性和维护性(父类有子类的共性,子类有特性,在这种情况下就可以使用继承)。
在Java中实现继承时使用extents来实现,具体使用如下:
举例:
比如有一个Person的类,一个Student类,一个Teacher类,这三个类中Person类为父类,其他为子类Student类为子类,子类继承父类,具体代码如下:
public class Person
{
String name;
int age;
public void eat()
{
System.out.println("吃饭");
}
public void sleep()
{
System.out.println("睡觉");
}
}
public class Student extends Person{
public void Study()
{
System.out.println("学习");
}
}
public class Teacher extends Person{
public void Teach()
{
System.out.println("教书");
}
}
继承注意事项:
1.父类的私有成员,子类不能继承(父类成员中用private修饰的成员,子类不能继承的)
继承复用性与维护性
继承可以提高代码的复用性和维护性主要是因为如果子类继承父类,想要对子类进行一些功能的修改以及完善时,那么就可以直接在父类中进行代码的修改而不需要在逐个子类中进行修改,这样的话就大大提高了代码的维护性;复用性主要是因为一个父类可以有多个子类来继承,就像上述代码一样,有两个子类可以继承父类。
继承的弊端:
让类与类之间产生了父子关系,增加了耦合性。耦合性:子类与父类之间的共性就会造成耦合。在软件设计过程中应该遵循一个原则,高内聚,低耦合。
高内聚:一个类独立完成某些功能的能力;
耦合:完成一个功能,要去依赖别的类
继承的语法特点:
1.在Java中只支持单继承(一个子类只能继承一个父类,一个父类可以有多个子类)
2.Java中也支持多层继承,多层继承即为“子继承父亲,父亲继承“父亲的父亲””
举例代码如下:
class Grandfather {
String g = "ggggg";
public void show() {
System.out.println("爷爷类中的show方法");
}
}
class Father extends Grandfather {
String f = "ffff";
public void fuShow() {
System.out.println("父亲的show方法");
}
}
class Grandson extends Father {
}
//测试
public class MyTest {
public static void main(String[] args) {
Grandson grandson = new Grandson();
System.out.println(grandson.g);
System.out.println(grandson.f);
grandson.show();
grandson.fuShow();
}
}
实现结果如下:
ggggg
ffff
爷爷类中的show方法
父亲的show方法
//这段代码即可以解释继承的多层继承
继承的注意事项
1.父类的私有成员,子类不能继承(父类成员中用private修饰的成员,子类不能继承的)
public class MyTest {
public static void main(String[] args) {
Zi zi = new Zi();
System.out.println(zi.name);
System.out.println(zi.f);
System.out.println(zi.num);
//System.out.println(zi.bb);(由于父类中private,因此在这里不能使用,否则会报错)
zi.fuShow();
zi.fuShow2();
zi.fuShow3();
//zi.fuShow4();(由于父类中private,因此在这里不能使用,否则会报错)
}
}
class Fu{
public Fu() {
}
String name="aaa";
public String f="fffff";
protected int num=200;
private int bb=2000;//子类不继承
public void fuShow(){
}
void fuShow2() {
System.out.println("Show2");
}
protected void fuShow3() {
System.out.println("Show3");
}
private void fuShow4() {
System.out.println("Show4");
}//子类不继承
}
class Zi extends Fu{
}
实现结果:
aaa
fffff
200
Show2
Show3
//父类成员中用private修饰的成员,子类不能继承的
2.构造方法不参与继承
3.不要为了继承而去继承(父类中的方法有很多,如果子类中具体使用只使用父类中的一两个方法,那么不需要去继承,如果父类中大部分方法子类都会使用,那么就可以使用继承)
4.在使用继承是要注意,继承时必须满足,子类是父类的一种,在这种情况下就可以使用继承。
继承中的方法重写
当子类与父类出现一模一样的方法时(方法名、参数、返回值一样),就会发生方法覆盖现象即方法重写。方法覆盖会导致子类方法会覆盖父类的方法。
方法重写的应用:子类需要父类的功能,而功能主体子类有自己特有的内容时,可以重写父类中的方法,这样即沿袭了父类的功能,又定义了子类特有的内容。
方法重写快捷键:ctrl+o(@Override //注解 可以检测该方法,是否是重写父类的方法)
举例:
父类代码块
public class Phone {
public void call(){
System.out.println("打电话");
}
public void sendMsg(){
System.out.println("发短信");
}
}
1.子类代码块之完全改写
public class Iphone extends Phone{
@Override
public void call() {
System.out.println("视频打电话");
}
}
2.子类代码块之继承父类功能并添加新的功能
public class XiaoMi extends Phone{
@Override
public void call() {
super.call();//沿袭父类的功能,super在下面进行解释
System.out.println("视频聊天");//添加新功能
System.out.println("语音聊天");//添加新功能
}
方法重写注意事项:
1.父类私有的方法子类不可以重写
2.子类在重写父类方法时,子类前面的权限修饰符不能低于父类的修饰符低,最好一样。
权限修饰符:public>protected>缺省的>private
变量访问的就近原则
当访问一个变量时,先在方法的局部范围值找,如果找到那么就直接使用。如果在局部范围内没有找到该变量就去本类的成员范围内找,找到就使用,如果在本类成员范围内仍然没有找到,就去父类的成员范围找,找到就使用,如果没有找到就是没有定义该变量。
进行变量访问时,如果局部变量,本类成员变量,父类变量重名时,想要访问不同变量,如果访问本类中的成员变量,那么就需要加this,如果访问父类中的变量,那么就需要加super(super表示的是父类的空间标识,在调用方法时与变量访问相似,使用super.方法名即可)。
举例如下:
public class MyTest {
public static void main(String[] args) {
Son son = new Son();
son.show(20);
}
}
class Father{
int num=200;
}
class Son extends Father{
int num=600;
public void show(int num){
System.out.println(num); //20
System.out.println(this.num); //600
System.out.println(super.num);//200
}
}
final关键字
final关键字
1.final可以修饰变量、成员方法、还可以修饰类;
2.final修饰变量,那么这个变量就会变为一个常量;
3.final修饰一个类,那么这个类将不能被继承;
4.final修饰方法,那么这个方法将不能被重写,子类只能继承使用
5.final修饰引用类型,那么其指向的地址值不能再次改变
代码执行顺序
当有继承、代码块、方法、以及静态方法时,代码执行顺序为:子类继承父类,首先初始化父类数据,由于存在静态方法,因此执行顺序如下:(1)父类静态代码块(2)子类静态代码块(3)父类代码块(4)父类方法(5)子类代码块(6)子类方法