java基础---继承

Posted 流着眼泪奔跑

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了java基础---继承相关的知识,希望对你有一定的参考价值。

1.为什么使用继承

将重复抽取到父类中,代码使用继承优化设计

2.使用继承优化

方便修改代码、减少代码量

子类与父类是is-a关系

3.如何使用继承

首先编写父类

class Pet {

//公共的属性和方法

}

然后编写子类,继承父类

     class Dog extends Pet {

//子类特有的属性和方法

}

class Penguin extends Pet {

}

 

一个子类只能继承一个父类

继承关键字:extends

举例:访问父类的构造结构

public abstract class Pet {

/*宠物类*/

private String name;

private int love;

private int health;

/*

 * get.set

 *

 * */

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public int getLove() {

return love;

}

public void setLove(int love) {

this.love = love;

}

public int getHealth() {

return health;

}

public void setHealth(int health) {

this.health = health;

}

 /*

  *

  * 带参数的方法

  *

  * */

public Pet(String name, int love, int health) {

super();

this.name = name;

this.love = love;

this.health = health;

System.out.println("父类有参的构造方法");

}

/*

 *

 *

 * 不带参数的方法

 *

 * */

public Pet() {

super();

System.out.println("父类无参的构造方法");

// TODO Auto-generated constructor stub

}

/*

 *

 * 打印print

 *

 * */

public void print(){

System.out.println("name="+name+"love"+love+"health"+health);

}

}

 

public class Dog extends Pet{

private String strain;

/*

 * get.set

 *

 * */

public String getStrain() {

return strain;

}

public void setStrain(String strain) {

this.strain = strain;

}

/*

  *

  * 带参数的方法

  *

  * */

public Dog(String name, int love, int health, String strain) {

super(name, love, health);

this.strain = strain;

System.out.println("子类有参构造方法");

}

/*

  *

  * 不带参数的方法

  *

  * */

public Dog() {

super();

System.out.println("子类无参构造方法");

// TODO Auto-generated constructor stub

}

}

 

public class Penguin extends Pet{

private String gender;

/*

 * get.set

 *

 * */

public String getGender() {

return gender;

}

public void setGender(String gender) {

this.gender = gender;

}

/*

  *

  * 带参数的方法

  *

  * */

public Penguin(String name, int love, int health, String gender) {

super(name, love, health);

this.gender = gender;

}

/*

  *

  * 不带参数的方法

  *

  * */

public Penguin() {

super();

// TODO Auto-generated constructor stub

}

}

 

public class Test {

public static void main(String[] args) {

      //初始化一个子类对象

      //首先初始化父类对象

    Dog d=new Dog("小黑", 99, 99, "动漫人物");  

}

}

 

心得:

super()表示代表父类的名字,只是把自己的属性初始化了,但是父类的属性还是由父类来初始化

使用了继承,必然会初始化父类对象

举例:访问父类的方法、属性

public abstract class Pet {

/*宠物类*/

private String name;

private int love;

private int health;

/*

 * get.set

 *

 * */

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public int getLove() {

return love;

}

public void setLove(int love) {

this.love = love;

}

public int getHealth() {

return health;

}

public void setHealth(int health) {

this.health = health;

}

 /*

  *

  * 带参数的方法

  *

  * */

public Pet(String name, int love, int health) {

super();

this.name = name;

this.love = love;

this.health = health;

System.out.println("父类有参的构造方法");

}

/*

 *

 *

 * 不带参数的方法

 *

 * */

public Pet() {

super();

System.out.println("父类无参的构造方法");

// TODO Auto-generated constructor stub

}

/*

 *

 * 打印print

 *

 * */

/*public void print(){

System.out.println("name="+name+"love"+love+"health"+health);

}*/

}

 

 

public class Dog extends Pet{

private String strain;

/*

 * get.set

 *

 * */

public String getStrain() {

return strain;

}

public void setStrain(String strain) {

this.strain = strain;

}

/*

  *

  * 带参数的方法

  *

  * */

public Dog(String name, int love, int health, String strain) {

/*访问父类的带参数的构造方法*/

super(name, love, health);

this.strain = strain;

System.out.println("子类有参构造方法");

}

/*

  *

  * 不带参数的方法

  *

  * */

public Dog() {

super();

System.out.println("子类无参构造方法");

// TODO Auto-generated constructor stub

}

//重写

@Override

public void print() {

//访问父类的方法

        super.print();

                 //访问父类属性

System.out.println("name="+super.getName()+"love="+super.getLove()+"health="+super.getHealth());

}

}

 

public class Test {

public static void main(String[] args) {

 

    //有参数

    Dog dog===new Dog("小黑", 99, 99, "动漫人物");  

    dog.print();

}

}

心得:

访问父类私有属性name时,super.name报错,不能被访问,如果还想访问的话,可以使用get方法实现,如super.getName()

4.子类可以继承父类的所有些资源吗?

不能被继承的父类成员:private成员不能、子类与父类不在同包,使用默认访问权限的成员、构造方法

举例:

public abstract class Pet {

/*宠物类*/

private String name;

private int love;

private int health;

//默认访问权限

int num;

/*

 * get.set

 *

 * */

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public int getLove() {

return love;

}

public void setLove(int love) {

this.love = love;

}

public int getHealth() {

return health;

}

public void setHealth(int health) {

this.health = health;

}

 /*

  *

  * 带参数的方法

  *

  * */

public Pet(String name, int love, int health) {

super();

this.name = name;

this.love = love;

this.health = health;

System.out.println("父类有参的构造方法");

}

/*

 *

 *

 * 不带参数的方法

 *

 * */

public Pet() {

super();

System.out.println("父类无参的构造方法");

// TODO Auto-generated constructor stub

}

/*

 *

 * 打印print

 *

 * */

 

public void print(){

System.out.println("name="+name+"love"+love+"health"+health);

}    

}

 

 

public class Dog extends Pet{

private String strain;

/*

 * get.set

 *

 * */

public String getStrain() {

return strain;

}

public void setStrain(String strain) {

this.strain = strain;

}

/*

  *

  * 带参数的方法

  *

  * */

public Dog(String name, int love, int health, String strain) {

/*访问父类的带参数的构造方法*/

super(name, love, health);

this.strain = strain;

System.out.println("子类有参构造方法");

}

/*

  *

  * 不带参数的方法

  *

  * */

public Dog() {

super();

System.out.println(super.num);  //默认访问权限

System.out.println("子类无参构造方法");

// TODO Auto-generated constructor stub

}   

//重写

@Override

public void print() {

 super.print();

 Sysotem.out.println(super.num)在同一个包下使用默认权限可访问

}

}

 

package demo2;

public class Cat extends Pet{

private String eyeColor;

public String getEyeColor() {

return eyeColor;

}

public void setEyeColor(String eyeColor) {

this.eyeColor = eyeColor;

}

public Cat() {

super();

// TODO Auto-generated constructor stub

}

public Cat(String eyeColor) {

super();

this.eyeColor = eyeColor;

}

/*不同包不可使用*/

private void print() {

System.out.println(num);

}

}

5.访问修饰符总结

记住有几个

 

 6.多重继承关系的初始化顺序是怎样的

Animal--pet--dog  假设它们都是继承类,new一个Dog的无参方法,调用无参方法之前先必须调用pet()构造方法,调用pet方法有发现需要先调用animal方法

 

 

7.何时使用继承

继承与真实世界类似,符合is-a关系的设计使用继承

继承是代码重用的一种方式、将子类共有的属性和行为放到父类中

8.使用继承后效果

调用父类的print()方法,不能显示Dog的strain信息

举例:

public abstract class Pet {

/*宠物类*/

private String name;

private int love;

private int health;

/*

 * get.set

 *

 * */

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public int getLove() {

return love;

}

public void setLove(int love) {

this.love = love;

}

public int getHealth() {

return health;

}

public void setHealth(int health) {

this.health = health;

}

 /*

  *

  * 带参数的方法

  *

  * */

public Pet(String name, int love, int health) {

super();

this.name = name;

this.love = love;

this.health = health;

}

/*

 *

 *

 * 不带参数的方法

 *

 * */

public Pet() {

super();

// TODO Auto-generated constructor stub

}

/*

 *

 * 打印print

 *

 * */

public void print(){

System.out.println("name="+name+"love"+love+"health"+health);

}

}

 

public class Dog extends Pet{

private String strain;

/*

 * get.set

 *

 * */

public String getStrain() {

return strain;

}

public void setStrain(String strain) {

this.strain = strain;

}

/*

  *

  * 带参数的方法

  *

  * */

public Dog(String name, int love, int health, String strain) {

/*访问父类的带参数的构造方法*/

super(name, love, health);

this.strain = strain;

}

/*

  *

  * 不带参数的方法

  *

  * */

public Dog() {

super();

System.out.println(super.num);  //默认访问权限

// TODO Auto-generated constructor stub

}   

//重写

@Override

public void print() {

  print();*/

}

}

 

 

public class Test {

public static void main(String[] args) {

    //有参数

    Dog d===new Dog("小黑", 99, 99, "动漫人物");

    d.print();   

}

}

9.方法重写

子类重写父类方法,方法名不能变,返回值父类值的子类对象

10.方法重写的规则

n方法名相同

n参数列表相同

n返回值类型相同或者是其子类;

n访问权限不能严于父类

 

举例:

public abstract class Pet {

/*宠物类*/

private String name;

private int love;

private int health; 

//默认访问权限

int num;

/*

 * get.set

 *

 * */

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public int getLove() {

return love;

}

public void setLove(int love) {

this.love = love;

}

public int getHealth() {

return health;

}

public void setHealth(int health) {

this.health = health;

}

 /*

  *

  * 带参数的方法

  *

  * */

public Pet(String name, int love, int health) {

super();

this.name = name;

this.love = love;

this.health = health;

}

/*

 *

 *

 * 不带参数的方法

 *

 * */

public Pet() {

super();

// TODO Auto-generated constructor stub

}

/*

 *

 * 打印print

 *

 * */

public void print(){

System.out.println("name="+name+"love"+love+"health"+health);

}

}

 

 

public class Dog extends Pet{

private String strain;

/*

 * get.set

 *

 * */

public String getStrain() {

return strain;

}

public void setStrain(String strain) {

this.strain = strain;

}

/*

  *

  * 带参数的方法

  *

  * */

public Dog(String name, int love, int health, String strain) {

super(name, love, health);

this.strain = strain;

}

/*

  *

  * 不带参数的方法

  *

  * */

public Dog() {

super();

// TODO Auto-generated constructor stub

}

//重写

@Override

public void print() {   System.out.println("name="+super.getName()+"love="+super.getLove()+"health="+super.getHealth()+"strain="+strain);

}

}

 

 

public class Test {

public static void main(String[] args) {

    //有参数

    Dog d===new Dog("小黑", 99, 99, "动漫人物");

    d.print();   

}

}

11.super关键字来访问父类的成员

super只能出现在子类的方法和构造方法中

super调用构造方法时,只能是第一句

super不能访问父类的private成员

 

 

练习:车辆的运行

package lx;

public class Motor {

private String pl;

private String qgs;

private String xh;

 

public String getPl() {

return pl;

}

public void setPl(String pl) {

this.pl = pl;

}

public String getQgs() {

return qgs;

}

public void setQgs(String qgs) {

this.qgs = qgs;

}

public String getXh() {

return xh;

}

public void setXh(String xh) {

this.xh = xh;

}

public Motor(String pl, String qgs, String xh) {

super();

this.pl = pl;

this.qgs = qgs;

this.xh = xh;

}

public Motor() {

super();

// TODO Auto-generated constructor stub

}

 

//自己的方法

public void work(){

System.out.println("发动机开始工作");

}

//

}

 

 

package lx;

public class Car extends Motor {

private String fdj;

private String cp;

private String cx;

 

public String getFdj() {

return fdj;

}

public void setFdj(String fdj) {

this.fdj = fdj;

}

public String getCp() {

return cp;

}

public void setCp(String cp) {

this.cp = cp;

}

public String getCx() {

return cx;

}

public void setCx(String cx) {

this.cx = cx;

}

public Car(String pl, String qgs, String xh, String fdj, String cp,

String cx) {

super(pl, qgs, xh);

this.fdj = fdj;

this.cp = cp;

this.cx = cx;

}

public Car() {

super();

// TODO Auto-generated constructor stub

}

    //

public void run(){

System.out.println("车牌为:"+cp+"的"+cx+"启动....");

super.work();

System.out.println("型号:"+super.getXh());

System.out.println("排量:"+super.getPl());

System.out.println("汽缸数:"+super.getQgs());

}

}

 

 

package lx;

public class CarTest {

public static void main(String[] args) {

Car car=new Car("3000", "12", "奔馳330", "奔馳330", "金A123456", "寶馬");

car.run();

}

}

12.抽象类

实例化Pet没有意义

Pet pet = new Pet ("贝贝",20,40);

pet.print();

13.如何避免/限制实例化(关键字abstract

abstract也可用于抽象类

举例

public abstract class Pet {

}

abstract作用限制一个类的实例化,这个类的存在是为了帮助其他类,实例化这个类无意义,让这个类无法做对象了

abstract也可用于-抽象方法

举例:

public abstract class Pet {

public void print() {

//…

}

}

抽象方法没有方法体

抽象方法必须在抽象类里(类是抽象的,方法可以是抽象的可以不是,一旦方法是抽象的,类必须是抽象的)

抽象方法必须在子类中被实现,除非子类是抽象类

举例:

public abstract class Pet {

/*宠物类*/

private String name;

private int love;

private int health;

/*

 * get.set

 *

 * */

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public int getLove() {

return love;

}

public void setLove(int love) {

this.love = love;

}

public int getHealth() {

return health;

}

public void setHealth(int health) {

this.health = health;

}

 /*

  *

  * 带参数的方法

  *

  * */

public Pet(String name, int love, int health) {

super();

this.name = name;

this.love = love;

this.health = health;

System.out.println("父类有参的构造方法");

}

/*

 *

 *

 * 不带参数的方法

 *

 * */

public Pet() {

super();

System.out.println("父类无参的构造方法");

// TODO Auto-generated constructor stub

}

/*抽象方法*/

public abstract void print();

}

 

public class Dog extends Pet{

private String strain;

/*

 * get.set

 *

 * */

public String getStrain() {

return strain;

}

public void setStrain(String strain) {

this.strain = strain;

}

/*

  *

  * 带参数的方法

  *

  * */

public Dog(String name, int love, int health, String strain) {

super(name, love, health);

this.strain = strain;

}

/*

  *

  * 不带参数的方法

  *

  * */

public Dog() {

super();

// TODO Auto-generated constructor stub

}

//必须重写

@Override

public void print() {   System.out.println("name="+super.getName()+"love="+super.getLove()+"health="+super.getHealth()+"strain="+strain);

}

}

14.final用法

1-某个类不希望被继承前面加final

最终版的类

public final class Penguin extends Pet {

//

}

2-方法不希望被重写

        最终版的方法

        public final void print () {

//

}

3-属性值不希望被修改

        最终版的属性值

        public class Penguin {

final String home ="南极";// 居住地

public void setHome(String name){

this.home=home; //错误,不可再赋值

}

}

 

举例1:修饰类

package Final;

public final class Person {

private String name;

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public Person(String name) {

super();

this.name = name;

}

public Person() {

super();

// TODO Auto-generated constructor stub

}

public final void Person() {

 System.out.println("你好");

}

}

 

package Final;

public class Test extends Person {

/*

 * 出现错误:修饰类

 * The type Test cannot subclass the final class Person*/

}

 

举例2:修饰方法

package Final;

public  class Person {

private String name;

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public Person(String name) {

super();

this.name = name;

}

public Person() {

super();

// TODO Auto-generated constructor stub

}

public final void Person() {

 System.out.println("你好");

}

}

 

 

package Final;

public class Test1 extends Person {

/*

 *

 * 错误:修饰方法

 * 父类的f方法是final类型,不可重写!

 *

 * */

     public void print(){

          }

}

 

 

举例3:修饰属性

package Final;

public  class Person {

private String name;

public final int num=10;

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public Person(String name) {

super();

this.name = name;

}

public  void print() {

 System.out.println("你好");

}

}

 

package Final;

public class Test2 extends Person {

/*

 *

 * 错误:属性值不希望被修改

 *

 *

 * */

  private void print1() {

// TODO Auto-generated method stub

         System.out.println(num);

         num=20;

}

}

 

补充:同时使用staticfinal关键字

static final用来修饰成员变量和成员方法,可简单理解为“全局常量”,

对于变量,表示一旦给值就不可修改,并且通过类名可以访问。

对于方法,表示不可覆盖,并且可以通过类名直接访问。

15.常见错误

使用变量final修饰引用型变量,不可以再指向另外的对象

final Dog dog = new Dog("欧欧");

dog = new Dog("亚亚");

练习

package lx2;

public abstract class MotorVehicle {

private String no;

private String brand;

private String color;

private String mileage;

public MotorVehicle(String no, String brand, String color, String mileage) {

super();

this.no = no;

this.brand = brand;

this.color = color;

this.mileage = mileage;

}

public MotorVehicle() {

super();

// TODO Auto-generated constructor stub

}

public String getNo() {

return no;

}

public void setNo(String no) {

this.no = no;

}

public String getBrand() {

return brand;

}

public void setBrand(String brand) {

this.brand = brand;

}

public String getColor() {

return color;

}

public void setColor(String color) {

this.color = color;

}

public String getMileage() {

return mileage;

}

public void setMileage(String mileage) {

this.mileage = mileage;

}

/*

 * 計算租賃價格、

 * */

public abstract double calcRent(int days);  

   }

 

 

package lx2;

/*

 * 小轿车

 * final不可以被继承

 *

 * */

public final class  Car extends MotorVehicle{

private String type;

public String getType() {

return type;

}

public void setType(String type) {

this.type = type;

}

public Car(String no, String brand, String color, String mileage,

String type) {

super(no, brand, color, mileage);

this.type = type;

}

public Car() {

super();

// TODO Auto-generated constructor stub

}

/*

 * 小轎車租賃方法

 * */

@Override

public double calcRent(int days) {

        double rent=0;

        String type=this.type;

        if(type.equals("550i")) {

         rent=500*days;

        }else if(type.equals("別克商務艙GL8")) {

         rent=600*days;

        }else if(type.equals("別克林蔭大道")) {

         rent=300*days;

        }

return rent;

}

}

 

 

package lx2;

public final class Bus extends MotorVehicle{

private int  seatCount;

public int getSeatCount() {

return seatCount;

}

public void setSeatCount(int seatCount) {

this.seatCount = seatCount;

}

public Bus(String no, String brand, String color, String mileage,

int seatCount) {

super(no, brand, color, mileage);

this.seatCount = seatCount;

}

public Bus() {

super();

// TODO Auto-generated constructor stub

}

    /*

     *

     * 客车租赁价格

     *

     *

     * */

@Override

public double calcRent(int days) {

        double rent=0;

        int seat=this.seatCount;

        if(seat<16) {

         rent=800*days;

        }else {

         rent=1500*days;

        }

return rent;

}

}

 

package lx2;

import java.util.Scanner;

public class Test {

public static void main(String[] args) {

Scanner input=new Scanner(System.in);

int days=0;

int choice=0;

Car car=null;

Bus bus=null;

double rent=0;

System.out.println("*************");

System.out.println("欢迎");

System.out.println("请输入您要租的天数");

days=input.nextInt();

System.out.println("请选择租车类型:1-轿车;2-客车");

choice=input.nextInt();

switch (choice) {

case 1:

  //轎車

System.out.println("请输入轿车的品牌:1-宝马;2-别克");

String brand=null;

String type=null;

String no="赣A123456";

String color="红色";

String mileage="2万公里";

choice=input.nextInt();

if (choice==1) {

brand="宝马";

System.out.println("请选择您的型号;1-550i");

choice=input.nextInt();

if (choice==1) {

type="550i";

}

}else if(choice==2){

brand="别克";

System.out.println("请选择您的型号:1-別克商務艙GL8;2-別克林蔭大道");

 choice=input.nextInt();

    if(choice==1) {

     type="別克商务仓GL8";

    }else if(choice==2) {

     type="別克林阴大道";

    }

}

  //初始化小轎車

   car=new Car(no, brand, color, mileage, type);

   rent=car.calcRent(days);

   System.out.println("分配給您的車牌號是"+no);

break;

        case 2:

         //客車

   String brand2=null;//轎車品牌

   int seatCount=0;//轎車的座位數

   String no2="贛A123456";

   String color2="紅色";

   String mileage2="5萬公里";

   System.out.print("請選擇客車的品牌;1-金杯;2-金龍");

   choice=input.nextInt();

   if(choice==1) {

    brand="金杯";

   }else if(choice==2) {

    brand="金龍";

   }

   System.out.print("請輸入座位數目");

   seatCount=input.nextInt();

   bus=new Bus(no2, brand2, color2, mileage2, seatCount);

   rent=bus.calcRent(days);

   System.out.println("分配給您的車牌號是"+no2);

   break;  

  default:

  System.out.println("對不起,輸入錯誤");

  break;

}

//結算 判斷租賃的車輛是轎車還是客車

System.out.println("租金為:"+rent);

}

}

以上是关于java基础---继承的主要内容,如果未能解决你的问题,请参考以下文章

Java12-java语法基础继承

java 基础

Java基础——面对对象-继承

Java面向对象基础

阿花宝宝 Java基础笔记 之 继承

JAVA基础整理-50.Java继承和多态