当前位置: 首页 > news >正文

Java语言程序设计——篇十(1)

在这里插入图片描述

     🌿🌿🌿跟随博主脚步,从这里开始→博主主页🌿🌿🌿

接口介绍

  • 接口
    • 概述
    • 接口定义
    • 接口的实现
      • 实战演练
    • 👅接口的继承
      • 实战演练
      • 实战演练
    • 接口的类型
    • 常量
      • 实战演练
    • 静态方法
    • 默认方法
      • 解决默认方法冲突
      • 实战演练

接口

概述

Java语言中所有的类都处于一个类层次结构中。
除Object类以外,所有类都只有一个直接父类,即子类与父类之间是单继承的关系,但不允许多重继承。
为了实现多重继承,java语言通过接口使得处于不同层次、甚至互不相关的类具有相同的行为。

接口定义

  • 接口定义了一种可以被类层次中任何类实现的行为的协议
  • 接口是常量、抽象方法、默认方法和静态方法的集合体
  • 接口可以实现多重继承
  • 接口声明使用interface关键字
  • 接口定义,包含接口声明和接口体两部分
[public或者省略] interface 接口名称 [extends 父接口名列表]{[public][static][final] 数据类型 成员变量名=常量;……[public][abstract] 返回值的数据类型 方法名(参数表);……[public] static 返回值的数据类型 方法名(参数表){方法体}……[public] default 返回值的数据类型 方法名(参数表){方法体}……}

例:

 public interface Eatable {接口被看作是一种特殊的类型。每个接口都被编译为独立的字节码文件。//抽象方法public abstract String howtoEat();
}

接口与抽象类相似:
   接口可以作为引用变量数据类型或类型转换的结果;
   接口与抽象类一样,不能用new运算符创建接口实例。
接口的抽象方法只有声明,没有实现。
抽象方法也可以省略修饰符,省略修饰符编译器自动加上public、abstract。
在这里插入图片描述
                 在这里插入图片描述

在这里插入图片描述

  • 接口的UML表示
    在这里插入图片描述
  • 接口通常表示某种能力,因此接口名后缀通常是able。

接口的实现

接口的实现:利用接口的特性来建造类的过程。类似于继承,但不是extends,而是使用implements。
接口实现的语法格式:

       class  类名称  implements  接口名表{……}

👀一个类实现一个接口应注意的问题:

  • 如果实现某接口的类不是abstract的抽象类,则在类的定义部分必须实现指定接口的所有抽象方法。
  • 一个类在实现某接口的抽象方法时,必须使用完全相同的方法头。
  • 接口中抽象方法被指定为public,所以类在实现方法时,必须显示地使用public修饰符。
  • 接口可以作为一种引用类型来使用,可以声明接口类型的变量或数组,并用它来访问实现该接口的类的对象。
    (通过接口类型的变量可以访问类所实现的接口的方法)

实战演练

【例】Orange实现Eatable接口。

 public interface Eatable {//抽象方法public abstract String howtoEat();
}
public class Orange @Overridepublic String howtoEat(){returnMake Orange Juice}
}

👅接口的继承

  • 定义一个接口时可通过extends关键字声明该新接口是某个已存在的父接口的派生接口。
  • 与类继承的区别:一个接口可以有一个以上的父接口,它们之间用逗号隔开,形成父接口列表。
  • 新接口将继承所有父接口的常量、抽象方法和默认方法,但不能继承父接口的静态方法(也不能被实现类所继承)。
  • 多重继承:一个子类可以有一个以上的直接父类,该子类可以继承它所有直接父类的成员。
  • Java语言虽不支持多重继承,但可以利用接口间接地解决多继承问题。
  • 一个类只能有一个直接父类,但是它可以同时实现若干个接口(Java中接口的主要作用是可以帮助实现多重继承。)。一个类实现多个接口时,在implements子句中用逗号分隔各个接口名。

实战演练

【例】接口继承多个接口。CC接口继承AA接口和BB接口

public interface AA { int STATUS = 100;public abstract void display();   
} 
public interface BB { public abstract void show();     public default void print(){     System.out.println("这个是接口BB的默认方法");}
}
public interface CC extends AA, BB{ int NUM = 3;    
}
public class DD implements CC {public void display() {System.out.println("接口AA的display方法");}public void show() {System.out.println("接口BB的show方法");}public static void main(String[] args) {DD dd = new DD();System.out.println(DD.STATUS);dd.show();dd.print(); AA aa = new DD();aa.display();}
}

运行结果:
在这里插入图片描述
解释代码:
上述AA、BB、CC接口与DD类之间的关系如图所示;图中虚线表示接口实现。
接口是允许多继承的,而类只能实现单继承。
在这里插入图片描述

实战演练

【例】类实现多个接口。AB类实现AA接口和BB接口

public class AB implements AA, BB{public void display(){System.out.println("接口AA的display方法");}   public  void show(){    System.out.println("接口BB的show方法");}
}

类实现多个接口需实现每个接口中的抽象方法。接口中的常量和默认方法都被继承了,但接口中的静态方不被继承

接口的类型

接口也是一种引用类型,任何实现该接口的实例都可以存储在该接口类型的变量中。

AA aa = new DD();         // 向上自动类型转换
BB bb = new DD();
CC cc = new DD();

当通过接口对象调用某个方法时,Java运行时系统确定该调用哪个类中的方法。

aa.display();   // 调用实现类的方法  
bb.show();    
cc.print();    // 调用继承的默认方法

常量

定义在接口中的任何变量都自动加上public、final、static属性,因此它们都是常量,常量的定义可以省略修饰符,下面三行代码效果相同。

 int STATUS = 100;public int STATUS = 100;public final static int STATUS = 100;

不推荐在接口中定义常量,使用枚举类型描述一组常量集合比接口常量更好。

实战演练

1.设计一个名为Swimmable的接口,其中包含void swim()方法,设计另一个名为Flyable的接口,其中包含void fly()方法。
2.定义一个Duck类实现上述两个接口。

// Swimmable接口  
interface Swimmable {  void swim();  
}  // Flyable接口  
interface Flyable {  void fly();  
}  // Duck类实现Swimmable和Flyable接口  
class Duck implements Swimmable, Flyable {  // 实现Swimmable接口的swim方法  @Override  public void swim() {  System.out.println("The duck is swimming.");  }  // 实现Flyable接口的fly方法  @Override  public void fly() {  System.out.println("The duck is flying.");  }  // 可以在Duck类中添加其他方法和属性  
}  // 测试类  
public class Main {  public static void main(String[] args) {  Duck duck = new Duck();  duck.swim(); // 调用swim方法  duck.fly();  // 调用fly方法  }  
}

在这个例子中,SwimmableFlyable是两个接口,它们分别定义了swimfly方法。Duck类通过implements关键字实现了这两个接口,因此它必须提供这两个方法的具体实现。在main方法中,我们创建了一个Duck对象,并调用了它的swimfly方法,输出了相应的信息。

静态方法

  • 在Java 8中,可以在接口中定义静态方法,定义静态方法使用static关键字,默认的访问修饰符是public。
  • 接口的静态方法不能被子接口继承,也不被实现类继承。
  • 接口中的静态方法不能被子接口和实现类继承,访问形式为:接口名.静态方法名( )。
public interface SS {int STATUS = 100;                    public static void display() {System.out.println(STATUS);}
}

默认方法

  • 接口中的默认方法用default修饰符来定义,默认方法可以被子接口或被实现该接口的类所继承。访问形式为:对象名.默认方法名( )。
  • 子接口中若定义名称相同的默认方法,则父接口中的默认方法被隐藏。
public interface BB { public void show();     public default void print(){     System.out.println("这个是接口BB的默认方法");}
}

解决默认方法冲突

  • 如果子接口中定义了与父接口同名的常量或者相同的方法,则父接口中的常量被隐藏,方法被覆盖。
  • 但在接口的多重继承中可能存在常量名或方法名重复的问题,即名字冲突问题。
  • 对于常量,若名称不冲突,子接口可以继承多个父接口中的常量,如果多个父接口中有同名的常量,则子接口不能继承,但子接口中可以定义一个同名的常量。
  • 对于多个父接口中存在同名的方法时,此时必须通过特殊的方式加以解决。
  • 在多个父接口的实现类中解决同名默认方法的名字冲突问题有两种方法:一种是提供同名方法的一个新实现;另一种是委托一个父接口的默认方法。
  • 如果两个父接口有一个提供的不是默认方法,而是抽象方法,则在实现类中提供同名方法的一个新实现即可。
  • 如果一个类继承了一个父类并实现了一个接口,而从父类和接口中继承了同名的方法,此时采用“类比接口优先”的原则,即只继承父类的方法,而忽略来自接口的默认方法。

实战演练

【例】在两个接口Person和Identified中定义的同名默认方法getID ( ),在实现类中委托其中一个父接口的默认方法

public interface Person { public String getName();public default int getID(){return 0;}
}
public interface Identified {public default int getID(){return Math.abs(hashCode());}
}
public class Employee implements Person, Identified { String name;@Overridepublic String getName(){return this.name;}    public int getID(){ return Identified.super.getID();} // 为getID()方法提供一个新的实现
}

博主用心写,读者点关注,互动传真情,知识不迷路。

http://www.lryc.cn/news/410033.html

相关文章:

  • Qt对比MFC优势
  • RuntimeError: No CUDA GPUs are available
  • URL参数中携带中文?分享 1 段优质 JS 代码片段!
  • sass的使用
  • 【足球走地软件】走地数据分析预测【大模型篇】走地预测软件实战分享
  • 现在有什么赛道可以干到退休?
  • c程序杂谈系列(职责链模式与if_else)
  • 前端开发技术之CSS(层叠样式表)
  • go语言day20 使用gin框架获取参数 使用自定义的logger记录日志
  • DHCP笔记
  • TCP为什么需要四次挥手?
  • MySQL 索引相关基本概念
  • Neutralinojs教程项目实战初体验(踩坑指南),干翻 electron
  • 【轻松拿捏】Java-List、Set、Map 之间的区别是什么?
  • 用户史订单查询业务
  • 第8节课:CSS布局与样式——掌握盒模型与定位的艺术
  • electron 主进程和渲染进程
  • redis的高可用及性能管理和雪崩
  • php基础语法
  • js抓取短信验证码发送
  • 视频怎么加密?常见的四种视频加密方法和软件
  • 聚焦全局应用可用性的提升策略,详解GLSB是什么
  • 无水印下载视频2——基于tkinter完成头条视频的下载
  • Java学习Day17:基础篇7
  • Vue3 Pinia的创建与使用代替Vuex 全局数据共享 同步异步
  • 手撕数据结构02--二分搜索(附源码)
  • 单片机工程师继续从事硬件设计还是涉足 Linux 开发?
  • 《昇思25天学习打卡营第25天|第28天》
  • Flutter Dio网络请求报错FormatException: Unexpected character
  • 关于@JsonSerialize序列化与@JsonDeserialize反序列化注解的使用(密码加密与解密举例)