JAVA面向对象——抽象类与多态

1 篇文章 0 订阅
1 篇文章 0 订阅

一,抽象类

定义:抽象类就是含有抽象方法的类,在解决实际问题时,一般将父类定义为抽象类,需要使用这个父类进行继承与多态处理,回想继承和多态的原理,继承树越是在上方的类越抽象。抽象类无法通过创建对象来实现,只能通过子类重写来实现
抽象类的定义:
使用abstract关键字定义,而使用这个关键字定义的方法称之为抽象方法。抽象方法没有方法体,这个方法本身没有任何意义,除非他被子类重写,实际上抽象类除了被继承之外没有任何意义。

public abstract class Test{
	abstract void eat();//抽象方法
}

抽象类的特点:
1. 不能new 出来 只能靠子类实现;
2. 抽象类可以写普通方法;
3. 抽象方法必须在抽象类中;
4. 子类如果不是抽象类则必须覆写抽象类之中的全部抽象方法(如果子类没有实现父类的抽象方法,则必须将子类也定义为为abstract类。);
5. 普通类对象可以直接实例化,但抽象类的对象必须经过向上转型之后才可以得到。
6. 抽象方法必须为public或者protected(因为如果为private,则不能被子类继承,子类便无法实现该方法),缺省情况下默认为public;

虽然一个类的子类可以去继承任意的一个普通类,可是从开发的实际要求来讲,普通类尽量不要去继承另外一个普通类,而是去继承抽象类。

抽象类的使用限制

  1. 外部抽象类不允许使用static声明,而内部的抽象类运行使用static声明。使用static声明的内部抽象类相当于一个外部抽象类,继承的时候使用“外部类.内部类”的形式表示类名称。
  2. 不能使用final修饰符修饰抽象类和抽象方法;

二,多态

首先我们要明白的是多态得前提条件是继承,然后就是多态为方法的多态与属性没有关系

多态三要素:
1. 编写具有继承关系的父类和子类
2. 子类重写父类的方法
3. 使用父类引用指向子类的对象

多态要注意 的细节:
1. 多态情况下,子父类存在同名的成员变量时,访问的是父类的成员变量。
2. 多态情况下,子父类存在同名的非静态的成员函数时,访问的是子类的成员函数。
3. 多态情况下,子父类存在同名的静态的成员函数时,访问的是父类的成员函数。

多态的作用:
1. 多态用于形参类型的时候,可以接收更多类型的数据 。
2. 多态用于返回值类型的时候,可以返回更多类型的数据。

说到多态不得不说到的就是子父类之间的类型转换,其实也可以通过我们JAVA中基本类型的转换来理解,当我们把一个较小的类型转为大的时候,可以系统会为我们进行自动转换,而将一个大的转为小的时候就需要进行强制转换了,子父类之间进行转换也是同理。
如下代码:

public class Demo01 {
    
    public void look(){
        System.out.println("父类看方法");
    }
    
    
}

class Demo extends Demo01{

    @Override
    public void look() {
        System.out.println("子类看方法");
    }
    
    public void sleep(){
        System.out.println("睡觉");
    }
}

class Test01 {
    public static void main(String[] args) {
       Demo d1=new Demo();//不涉及转型

        Demo01 d2=new Demo();//子类转为父类,也称之为向上转型,父类引用指向子类

 		 Demo d3=new Demo01();//编译出错,子类引用无法指向父类对象
 		 
        d2.look();//此时d2为父类对象,但是调用的look方法为子类的,因为子类重写了look方法
        
        d2.sleep();//编译出错,因为d2为父类对象,所以调不到sleep方法   

		((Demo)d2).sleep();//通过强转为子类对象就可以调用子类的sleep方法了
    }
}

从上面语句中我们可以总结出子父类之间的转换规则:

  1. 将一个父类的引用指向一个子类对象,称之为向上转型,自动转换类型,这个对象只能调用父类独有和子父类之间都有的方法,如果子类重写了父类的方法则会调用子类重写后的方法,无法调用子类独有的方法;
  2. 子类引用无法指向父类对象,父类对象可以通过强行转换来调用子类独有的方法,一般不这样做,因为大转小会丢失精确度;

instanceof关键字:用来判断对象与类之间是否存在继承关系如果存在返回true,否则返回false,左边是对象,右边是类

使用父类作为方法形参实现多态
这里便要用到我们上面讲到的关键字instanceof,在程序中一个父类有多个子类,而需要这些子类对象实现相同功能时就会产生很多重复代码,这是我们可以通过写一个方法来传对象方法的形参就是父类对象,用instanceof来进行判断传入的对象是否与类存在继承关系,如果存在就执行对应的方法体;
如下代码:

public class Animla { //动物类
    private String type;

    public String getType() {
        return type;
    }

    public void setType(String type) {
        this.type = type;
    }
}

class Cat extends Animla{ //猫类 继承动物类

    public Cat(String type){
        super.setType(type);
    }
}

class Dog extends Animla{ //狗类 继承动物类
    public Dog(String type){
        super.setType(type);
    }
}

class Temp{

    public void feed(Animla animla){
        if (animla instanceof Cat){
            System.out.println("猫吃鱼");
        }else if (animla instanceof Dog){
            System.out.println("狗吃骨头");
        }
    }

    public static void main(String[] args) {
        Temp t=new Temp();
        
        Dog dog=new Dog("狗");
        Cat cat=new Cat("猫");
        t.feed(dog);
        t.feed(cat);
    }
}

运行结果:

	狗吃骨头
	猫吃鱼

从上代码可以看出可以通过instanceof对传出对象的判断使同一个方法在不同场景中有不同作用。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值