分享一下我对接口的认识:

  一、认识接口

接口就像我们日常生活中,充电的插口,有两孔的,有三角形三孔的插座,插口定义了一个统一的规范,不同的插头,只要符合这个规范,就可以和插座对接,实现通电这一功能,而插座就是接口,所以我们发现,接口类似一种“标准”。

二、认识接口相关语法

  当我们右键 src 准备 New 一个 JavaClass 的时候,我们选择 interface 选项,输入接口名,就成功创建出了一个接口,接口是一个比抽象类还要抽象的东西。

1.接口内的变量默认由 public static final 修饰

2.接口内的方法默认由 public abstract 修饰

public interface IShape {
    public static final int a = 10;
    static final int b = 10;
    final int c = 10;
    int d = 10;

    public abstract void test();
    abstract void test2();
    void test3();
}

在接口中,怎么写都默认会帮你把没写的加上,当然,接口中可以有实现方法,不过这类方法需要被 static 或 default 修饰:

public interface IShape {
    
    default void func1(){
        System.out.println("func1被执行");
    }

    static void func2(){
        System.out.println("func2被执行");
    }
}

接口有的地方和抽象很像,因此其也可以被abstract修饰

public abstract interface IShape {

三、实现接口

  首先我们创造一个 Cycle 类,跟继承很像,我们在 Cycle 后添加 implements IShape 即可实现 IShape接口

public class Cycle implements IShape{
}

由于接口中的方法默认都是 public abstract 修饰的(default和static修饰的接口中的可具体实现方法不做讨论),所以在实现完接口后肯定会报错,因为子类并没有重写接口里的抽象方法

假设我们接口 IShape 中有 draw 这一抽象方法:

public abstract interface IShape {
    void draw();
}

接下来我们只需要在子类里重写draw方法即可:

public class Cycle implements IShape{
    @Override
    public void draw() {
        System.out.println("画一个圆圈");
    }
}

四、接口的应用

我们回到测试类 Test 中,在main方法里我们发现,接口不能实例化对象,但可以向上转型,并通过这一操作实现动态绑定:

public class Test {
    public static void main(String[] args) {
       // IShape iShape1 = new IShape();
        IShape iShape2 =new Cycle();
        iShape2.draw();
    }
}

我们发现 引用IShape 在调用 draw 方法时,将子类 Cycle 中的 draw 方法调出来了,所以说其实接口有很多地方跟抽象类很像,但接口比抽象类还要抽象。

五、接口中要注意的事项

首先,接口中的方法默认都是由 public abstract 修饰的,记住这个 public 。

我们在子类中重写接口的抽象方法时,要跟继承一样遵从“子类的重写方法访问权限要大于等于父类或接口的重写方法”,所以我们子类的这个重写的方法访问权限要>=public,学了四种访问修饰符的我们发现,也就只有 public 等于这个接口中默认 public 级访问权限的方法了,所以子类中的重写方法一定要由 public 修饰,不然一定会报错。

六、再次认识接口

接口不同于继承,继承相当于 is a 或者 a part of,比如 Dog extends Animal,狗是一个动物

Students extends School ,学生是学校的一部分等例子,接口相当于 can do,谁能做到什么行为,接口更像是一种划分规则。

比如说此时,我们创造了Dog Fish Duck Robot这几个类

此时,我们还有一些行为:Fly-飞,Run-跑,Swim-游泳

此时我们的父类Animal中有年龄,名字等成员变量,还有eat方法,那么跑,游泳,飞这些操作能写进父类Animal中吗?答案是不行,父类负责收集的动物们的共性,而有的动物会飞,有的会游泳,有的会跑,有的都会,有的会一部分,这都是要进一步划分的,难道我们要再创造一个父类Running来划分出会跑的吗?然后让Dog继承完Animal后再继承Running吗?答案是不行的,Java中子类无法同时继承多个父类,这个时候,就有了接口这一概念,我们的类可以实现,但继承+多实现,比如我们的鸭子 Duck ,它是动物,即会飞又会跑还会游泳


public class Duck extends Animal implements ISwimming,IRunning,IFly{

这就是单继承+多实现,实现接口更像是描述这个动物的特点,比如鸭子 can do 游泳, can do 跑, can do 飞 等等,还有,Robot机器人也会跑,当然也可以继承 IRunning 接口,这样 Robot 也会被视为 IRunning 类的了,当某个方法要求上传参数类型为 IRunning 的时候,我们不管是动物Duck,Dog,还是机器人 Robot 都可以上传,简单来说就是,接口不看你是不是动物,只看你能不能做到某件事,只要你机器人能跑,就可以和动物 Duck 被归为 IRunning  一类,这就是接口。

Logo

汇聚全球AI编程工具,助力开发者即刻编程。

更多推荐