抽象类和接口

1.抽象类

抽象类和抽象方法的详细说明

1. 抽象类的基本概念
  • abstract 修饰的类叫做抽象类
  • 抽象类必须是父类(抽象类不能作为其他类的子类)
  • 抽象类不能被实例化(不能创建对象)
  • 抽象类可以有构造方法 (虽然不能实例化,但子类可以通过 super() 调用)
java 复制代码
abstract class Animal { // 抽象类声明
    public Animal() { // 构造方法
        System.out.println("Animal constructor");
    }
}
2. 抽象方法的核心特性
  • abstract 修饰的方法叫做抽象方法
  • 抽象方法没有方法体(不包含具体实现)
  • 抽象方法必须在抽象类中声明(普通类不能有抽象方法)
  • 子类必须重写父类的所有抽象方法(除非子类也是抽象类)
java 复制代码
abstract class Animal {
    public abstract void eat(); // 抽象方法声明
}
3. 多态应用场景

抽象类虽然不能实例化,但可以通过父类引用指向子类对象的方式实现多态:

java 复制代码
Animal myDog = new Dog(); // 多态:Animal引用指向Dog对象
myDog.eat(); // 实际调用Dog类的eat()方法
4. 使用限制和冲突
  • 与final冲突
    • final 类不能被继承 → 与 abstract 必须作为父类的特性冲突
    • final 方法不能被重写 → 与 abstract 方法必须被重写的特性冲突
  • 与private冲突
    • private 成员对子类不可见 → 无法实现抽象方法
  • 与static冲突
    • static 方法属于类而非实例 → 与需要子类实现的特性冲突
5. 实现要求

子类继承抽象类时:

  1. 必须实现所有抽象方法
  2. 若不实现,则子类也必须声明为 abstract
  3. 通过 @Override 注解明确表明重写关系
java 复制代码
class Dog extends Animal {
    @Override
    public void eat() { // 必须实现抽象方法
        System.out.println("Dog is eating");
    }
}
6. 典型应用场景
  1. 框架设计 :定义通用行为规范

    java 复制代码
    abstract class DatabaseConnector {
        public abstract void connect();
        public abstract void disconnect();
    }
  2. 模板方法模式 :固定流程中的可变步骤

    java 复制代码
    abstract class Game {
        abstract void initialize();
        abstract void startPlay();
        // 固定流程方法
        public final void play() {
            initialize();
            startPlay();
        }
    }

2.接口

接口在Java中是一种完全抽象的类型定义,其核心特点主要体现在以下几个方面:

抽象方法的集合

  • 接口中的所有方法默认都是抽象方法(Java 8之前)

  • 从Java 8开始,接口中可以包含默认方法(使用default修饰)和静态方法

  • 示例:

    java 复制代码
    public interface Animal {
        void eat();  // 抽象方法
        default void sleep() {  // Java8默认方法
            System.out.println("Sleeping...");
        }
    }

实现规则

  • Java类不能多继承,但可以实现多个接口

  • 当一个类实现接口时,必须实现所有抽象方法(除非是抽象类)

  • 示例:

    java 复制代码
    public class Dog implements Animal {
        @Override
        public void eat() {
            System.out.println("Dog is eating");
        }
    }

成员限制

  • 接口中不能包含实例变量,但可以包含常量(public static final)

  • 示例:

    java 复制代码
    public interface Constants {
        int MAX_VALUE = 100;  // 默认为public static final
    }

构造与实例化

  • 接口没有构造方法,不能直接实例化

  • 但可以通过多态方式使用:

    java 复制代码
    Animal myDog = new Dog();

接口继承

  • 接口可以继承多个其他接口

  • 示例:

    java 复制代码
    public interface Pet extends Animal, Playable {
        void beFriendly();
    }

实现要求

  • 非抽象类实现接口时,必须提供所有抽象方法的具体实现
  • 如果实现多个接口且有相同方法签名,只需要实现一次

案例:

java 复制代码
package com.qcby;

// 实现Comparable接口,指定泛型为Person
public class Person implements Comparable{
    public Integer age;
    public String name;
    public Integer height;

    public Person(String name, Integer age, Integer height) {
        this.name = name;
        this.age = age;
        this.height = height;
    }
    @Override
    public String toString() {
        return "Person{" +
                "age=" + age +
                ", name='" + name + '\'' +
                ", height=" + height +
                '}';
    }

    // 重写compareTo方法
    @Override
   public int compareTo(Object o) {//排序接口Comparable
       //age - ((Person)o).age从小到大排序
       //((Person)o).age - age从大到小排序
       return age - ((Person)o).age;
   }
}
java 复制代码
package com.qcby;

public class ArraysDemo {
    /**
     * Object是所有类的父类 向上转型
     * @param o
     */
    public static void sort(Object[] o){
        //将Object数组转换成Comparable数组
        Comparable[] arr = (Comparable[]) o;
        //这里能够实现强制类型转换是有一个前提的
        //就是要排序的类必须实现Comparable接口
        for(int i = 0; i < arr.length - 1; i++){
            for(int j = 0; j < arr.length - 1 - i; j++){
                //compareTo是 Comparable 接口中定义的核心方法
                /**
                 * 若返回值 > 0:表示 arr[j] 大于 arr[j+1];
                 * 若返回值 = 0:表示两个元素相等;
                 * 若返回值 < 0:表示 arr[j] 小于 arr[j+1]。
                 */
                if(arr[j].compareTo(arr[j+1]) > 0){
                    Comparable temp = arr[j];
                    arr[j] = arr[j+1];
                    arr[j+1] = temp;
                }
            }
        }
    }
}
java 复制代码
package com.qcby;

import java.util.Map;
import java.util.TreeMap;

public class Test {
    public static void main(String[] args) {
        Person p1 =new Person("小花",18,180);
        Person p2 = new Person("小王",19,180);
        Person p3 = new Person("小赵",20,170);

//        Map<Person,Person> map = new TreeMap<>();
//        map.put(p1,p1);
//        map.put(p2,p2);
//        map.put(p3,p3);
//        System.out.println(map);
        Person[] persons = new Person[]{p1,p2,p3};
        ArraysDemo.sort(persons);
        for (Person p:persons){
            System.out.println(p);
        }
    }
}

3.接口和抽象类的异同:

抽象类是对类的一种抽象,本身是一种设计模板;接口是对行为的抽象是一种行为抽象

抽象是用来提取子类当中的共性代码 接口重点用于隐藏和封装

接口的方法默认是public,所有方法都是抽象方法,在接口中不能有方法的实现(Java 8开始接口方法可以有默认实现),抽象类可以有非抽象方法

一个类可以实现多个接口,但是最多只能继承一个抽象类

一个类实现接口的话要实现接口的所有方法,而抽象不一定(因为抽象类当中可以用非抽象的方法)

相关推荐
亮剑20182 小时前
第2节:程序逻辑与控制流——让程序“思考”
开发语言·c++·人工智能
lly2024062 小时前
Go 语言接口
开发语言
霜绛2 小时前
C#知识补充(二)——命名空间、泛型、委托和事件
开发语言·学习·unity·c#
August_._2 小时前
【MySQL】SQL语法详细总结
java·数据库·后端·sql·mysql·oracle
Dxxyyyy2 小时前
零基础学JAVA--Day26(枚举类)
java·开发语言
好望角雾眠2 小时前
第四阶段C#通讯开发-6:Socket之UDP
开发语言·笔记·学习·udp·c#
黑屋里的马2 小时前
java的设计模式之桥接模式(Bridge)
java·算法·桥接模式
升鲜宝供应链及收银系统源代码服务2 小时前
升鲜宝生鲜配送供应链管理系统---PMS--商品品牌多语言存储与 Redis 缓存同步实现
java·开发语言·数据库·redis·缓存·开源·供应链系统
大佬,救命!!!2 小时前
python实现象棋
开发语言·python·学习笔记·pygame·少儿编程·记录成长