【Java SE】接口类型
在 Java
中,接口(Interface
)是一种引用类型,类似于特殊的抽象类,用于定义一组方法规范,而不提供具体的实现。接口可以包含成员属性,这些属性默认是常量。尽管每个类只能继承一个父类,但它可以实现多个接口。
接口语法
接口使用 interface
关键字定义。接口中可以包含成员属性和成员方法。成员属性通常由 public static final
修饰,定义时这些修饰符可以省略。在 Java 7
之前,接口中的所有方法都是公共抽象方法,没有方法体,并且可以省略 public
和 abstract
修饰符。从 Java 8
开始,接口可以包含静态方法(使用 static
修饰)和默认方法(使用 default
修饰),这意味着接口可以提供具体的方法实现。实现接口的类使用 implements
关键字来实现这些方法。
interface 接口名 {
属性;
方法(1.抽象方法 2.默认方法 3.静态方法);
}
class 类名 implements 接口{
类属性;
类方法;
必须实现的接口的抽象方法;
}
静态方法:在接口中定义的静态方法可以直接通过接口调用,而不需要实现该接口的类实例化。这种静态方法通常用于提供工具功能或帮助方法,便于在不依赖于接口实现的情况下使用。例如,可以在接口中定义一些常用的静态工具函数,方便所有实现类共享。
默认方法:default
方法的一个重要用途是“接口演化”。例如,如果类 A
实现了接口 CI
,而后该接口引入了一个新的方法,那么 A
类就需要修改其实现代码来适应这个变化。如果新方法被定义为 default
方法,并提供了默认实现,那么 A
类就无需修改代码。这种方式保证了“源代码兼容”,使得现有的接口实现能够平滑过渡到新版本接口,从而减少了对现有代码的影响。
注意:接口中的方法自动被视为
public
,而接口中的属性总是public static final
。此外,从Java 9
开始,接口中可以定义private
方法。private
方法可以是静态方法或实例方法。由于私有方法只能用于接口本身,因此私有方法的作用是作为接口中其他方法的辅助方法。
default 方法冲突
当在一个接口中定义一个默认方法,但在超类或另一个接口中也定义了同名的方法时,会引发二义性。为了解决这种冲突,需要遵循以下规则:
- 超类优先:如果超类提供了一个具体的方法,则同名且参数类型相同的默认方法将被覆盖。
- 接口冲突:如果一个接口和另一个接口都提供了同名的方法(无论是否为默认方法),那么在实现类中必须重新实现这个方法,以解决冲突。
接口的使用
// `JDK 8.0`之后
interface InterfaceDemo {
public void test1(); // public
default void test2() {}; // default
abstract void test3(); // abstract
public abstract void test4(); // public abstract
// 接口中是可以定义静态方法的
// 静态方法必须要有实现
// 且这个静态方法只能用public修饰(public可以省去)。
public static void main(String[] args){
System.out.println("Interface test.");
}
}
class ClassDemo implements InterfaceDemo {
@Override
public void test1() {
// TODO Auto-generated method stub
}
@Override
public void test2() {
// TODO Auto-generated method stub
}
@Override
public void test3() {
// TODO Auto-generated method stub
}
@Override
public void test4() {
// TODO Auto-generated method stub
}
}
在使用接口的过程中,需要注意:
-
接口不能被实例化
-
接口中抽象方法可以不用
abstract
修饰。比如void a();
实际上是abstactor void a();
-
一个普通类实现接口,就必须将该接口的所有方法都实现,而抽象类实现接口,可以不用实现接口的方法
-
一个类同时可以实现多个接口
-
接口中属性的访问形式:
接口名.属性名
-
接口中的属性只能是
public static final
。比如int a = 1
实际为public static final int a = 1
(必须初始化) -
一个接口不能继承其他类,但可以继承多个其他接口。比如
interface A extends B,C{}
-
接口的修饰符只能是
public
和默认,这点和类的修饰符一样