• Java-接口、继承与多态


    勤能补拙
    文章持续更新,可以微信搜索【小奇JAVA面试】第一时间阅读,回复【资料】获取福利,回复【项目】获取项目源码,回复【简历模板】获取简历模板,回复【学习路线图】获取学习路线图。

    在这里插入图片描述


    前言

    学习好继承和多态是面向对象开发语言中非常重要的一个环节,如果在程序中使用继承和多态得当,整个程序的架构将变得非常有弹性,同时可以减少代码的冗余性。继承机制的使用可以复用一些定义好的类,减少重复代码的编写。多态机制的使用可以动态调整对象的调用,降低对象之间的依存关系。为了优化继承与多态,一些类除了继承父类外还使用接口的形式。Java中的类可以同时实现多个接口,接口被用来简历类与类之间关联的标准。

    一、类的继承

    继承在面向对象开发思想中是一个非常重要的概念,它使整个程序架构具有一定的弹性,在程序中复用一些已经定义完善的类不仅可以减少软件开发周期,也可以提高软件的可维护性和可扩展性。

    例如:

    public class Parent {//父类
        Parent(){
            System.out.println("调用父类的Parent()构造方法");
        }
    }
    class SubParent extends Parent{
        SubParent(){
            System.out.println("调用子类的SubParent()构造方法");
        }
    
        public static void main(String[] args) {
            SubParent s = new SubParent();
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14

    二、Object类

    在开始学习使用class关键字定义类时,就应用到了继承原理,应为在Java中,所有的类都直接或间接继承了java.lang.Object类。Object类是比较特殊的类,它是所有类的父类,是Java类层中的最高层类。当创建一个类时,总是在继承,除非某个类已经指定要从其他类继承,否则它就是从java.lang.Object类继承而来的,可见Java中的每个类都源于java.lang.Object类,如String、Integer等类都是继承于Object类;除此之外,自定义的类也都继承于Object类。由于所有类都是Object子类,所以在定义类时,省略了extends Object关键字。

    在Object类中主要包括clone()、finalize()、equals()、toString()等方法,其中常用的两个方法为equals()和toString()方法。由于所有的类都是Object类的子类,所以任何类都可以重写Object类中的方法。

    1、getClass()方法

    getClass()方法是Object类定义的方法,它会返回对象执行时的Class实例,然后使用此实例调用getName()方法可以取得类的名称。
    语法如下:

    getClass().getname();
    
    • 1

    可以将getClass()方法与toString()方法联合使用。

    2、toString()方法

    toString()方法的功能是将一个对象返回为字符串形式,它会返回一个String实例。在实际的应用中通常重写toString()方法,为对象提供一个特定的输出模式。当这个类转换为字符串或与字符串连接时,将自动调用重写的toString()方法。

    3、equals()方法

    在自定义的类中使用equals()方法进行比较时,equals()方法默认实现是使用“==”运算符比较两个对象的引用地址,而不是比较对象的内容,所以要想真正做到比较两个对象的内容,需要在自定义类中重写equalse()方法。

    三、对象类型的转换

    对象类型的转换在Java编程中经常遇到,主要包括向上转型与向下转型操作。

    1、向上转型

    因为平行四边形是特殊的四边形,也就是说平行四边形是四边形的一种,那么就可以将平行四边形对象看作是一个四边形对象。例如,鸡是家禽的一种,而家禽是动物中的一类 ,那么也可以将鸡对象看作是一个动物对象。
    例如:

    class Quadrangle {
        public static void draw(Quadrangle q){
            //SomeSentence
        }
    }
    class Parallelogram extends Quadrangle{
        public static void main(String[] args) {
            Parallelogram p = new Parallelogram();
            draw(p);
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11

    平行四边形类继承了四边形类,四边形类存在一个draw()方法,它的参数是Quadrangle(四边形类)类型,而在平行四边形类的主方法中调用draw()时给予的参数类型却是Parallelogram(平行四边形类)类型的。这里一直在强调一个问题,就是平行四边形也是一种类型的四边形,所以可以将平行四边形类的对象看作是一个四边形类的对象,这就相当于“Quadrangle obj = new Parallelogram()”,就是把子类对象赋值给父类类型的变量,这种技术被称为“向上转型”。试想一下正方形类对象可以作为draw()方法的参数,梯形类对象同样也可以作为draw()方法的参数,如果在四边形类的draw()方法中根据不同的图形对象设置不同的处理,就可以做到在父类中定义一个方法完成各个子类的功能,这样可以使同一份代码毫无差别地运用到不同类型之上,这就是多态机制的基本思想

    2、向下转型

    通过向上转型可以推理出向下转型是将较抽象类转换为较具体的类。这样的转型通常会出现问题,例如,不能说四边形是平行四边形的一种、所有的鸟都是鸽子,因为这非常不合乎逻辑。可以说子类对象总是父类的一个实例,但父类对象不一定是子类的实例。

    例如:

    class Quadrangle {
        public static void draw(Quadrangle q){
            //SomeSentence
        }
    }
    class Parallelogram extends Quadrangle{
        public static void main(String[] args) {
            draw(new Parallelogram());
            //将平行四边形类对象看作是四边形对象,称为向上转型操作
            Quadrangle q = new Parallelogram();
            //Parallelogram p=q;
            //将父类对象赋予子类对象,这种写法是错误的
            //将父类对象赋予子类对象,并强制转换为子类型,这种写法是正确的
            Parallelogram p = (Parallelogram)q;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16

    四、使用instanceof操作符判断对象类型

    当在程序中执行向下转型操作时,如果父类对象不是子类对象的实例,就会发生ClassCastException异常,所以在执行向下转型之前需要养成一个良好的习惯,就是判断父类对象是否为子类对象的实例。这个判断通常使用instanceof操作符来完成。可以使用instanceof操作符判断是否一个类实现了某个接口,也可以用它来判断一个实例对象是否属于一个类。
    instanceof的语法格式如下;

    myobject instanceof ExampleClass
    
    • 1

    例如:

    class Quadrangle {
        public static void draw(Quadrangle q){
            //SomeSentence
        }
    }
    class Square extends Quadrangle{
        //SomeSentence
    }
    class Anything{
        //SomeSentence
    }
    class Parallelogram extends Quadrangle{
        public static void main(String[] args) {
            Quadrangle q = new Quadrangle();//实例化父类对象
            //判断父类对象是否为Parallelogram子类的一个实例
            if(q instanceof Parallelogram){
                Parallelogram p = (Parallelogram)q;//向下转型操作
            }
            //判断父类对象是否为Square子类的一个实例
            if(q instanceof Square){
                Square s = (Square) q;//进行向下转型操作
            }
            //由于q对象不为Anything类的对象,所以这条语句是错误的
            
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26

    五、方法的重载

    方法的重载就是在同一个类中允许同时存在一个以上的同名方法,只要这些方法的参数个数或类型不同即可。

    六、多态

    利用多态可以使程序具有良好的扩展性,并可以对所有类对象进行通用的处理。

    例如:

    class Quadrangle {
        //实例化保存四边形对象的数组对象
        private Quadrangle[] qtest = new Quadrangle[6];
        private int nextIndex = 0;
        public void draw(Quadrangle q){     //定义draw()方法,参数为四边形对象
            if(nextIndex < qtest.length){
                qtest[nextIndex] = q;
                System.out.println(nextIndex);
                nextIndex++;
            }
        }
    
        public static void main(String[] args) {
            //实例化两个四边形对象,用于调用draw()方法
            Quadrangle q = new Quadrangle();
            q.draw(new Square());   //以正方形对象为参数调用draw()方法
            q.draw(new Parallelogramgle()); //以平行四边形对象为参数调用draw()方法
        }
    
    }
    //定义一个正方形类,继承四边形类
    class Square extends Quadrangle{
        public Square(){
            System.out.println("正方形");
        }
    }
    //定义一个平行四边形类,继承四边形类
    class Parallelogramgle extends Quadrangle{
        public Parallelogramgle(){
            System.out.println("平行四边形");
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32

    在这里插入图片描述

    七、抽象类与接口

    1、抽象类

    在解决实际问题时,一般将父类定义为抽象类,需要使用这个父类进行继承与多态处理。回想继承和多态的原理,继承树中越是在上方的类越抽象,如鸽子类继承鸟类、鸟类继承动物类。在多态机制中,并不需要将父类初始化对象,我们需要的只是子类对象,所以在Java语言中设置抽象类不可以实例化对象,因为图形类不能抽象出任何一种具体图形,但它的子类却可以。
    抽象类的语法如下:

    public abstract class Test{
    	abstract void testAbstract();//定义抽象方法
    }
    
    • 1
    • 2
    • 3

    2、接口

    接口是抽象类的延伸,可以将它看作是纯粹的抽象类,接口中的所有方法都没有方法体。
    接口使用interface关键字进行定义,其语法如下:

    public interface drawTest{
    	void draw();//接口内的方法,省略abstract关键字
    }
    
    • 1
    • 2
    • 3

    在接口中定义的任何字段都自动是static和final的。

    八、总结

    这里的相关内容还没有整理完毕,文章后面持续更新,建议收藏。

    文章中涉及到的命令大家一定要像我一样每个都敲几遍,只有在敲的过程中才能发现自己对命令是否真正的掌握了。

    可以微信搜索【小奇JAVA面试】第一时间阅读,回复【资料】获取福利,回复【项目】获取项目源码,回复【简历模板】获取简历模板,回复【学习路线图】获取学习路线图。

  • 相关阅读:
    高效实用|ChatGPT指令/提示词/prompt/AI指令大全,基础版
    最长公共字符串后缀
    数字孪生背后:谁在构建真实的数字世界?
    Unity地面交互效果——4、制作地面凹陷轨迹
    Kubernetes(k8s)CNI(Calico)网络模型原理
    云原生:10分钟了解一下Kubernetes架构
    动态资源平衡:主流虚拟化 DRS 机制分析与 SmartX 超融合的实现优化
    男孩姓舒取什么名字好听
    算法-链表-反转链表
    java 8 stream API
  • 原文地址:https://blog.csdn.net/weixin_44096133/article/details/125985021