资讯专栏INFORMATION COLUMN

Java思想之容器implements与接口interface

MockingBird / 3029人阅读

摘要:类似于中的事件驱动函数,当有事件发生时候,通过回调函数,通知主函数。一旦或内的某个函数触发了某个事件,就能通过监听接口发送给主函数,类似中的事件回调函数。父类与子类通过实现接口调用,此时即为父类本身。

  

http://homeway.me/


0x01.About

查了一些国内资料,都说java中extended与implements的区别是,一个类只能有一个继承,一个类可以有多个容器。

后来去看了些国外资料。

在我理解上,interface就是一个公共的类,可以包含公共函数、变量。

Java接口是用于指定一组抽象方法的类来实现一个抽象类型。

当一个类实现一个接口,它必须继承所有的内声明的抽象方法,好像签订了一份合同,并履行协议。


0x02.Example

先来看看怎么声明一个接口,文件保存为 InterFace.java

public class InterFace {
    public static void main(String[] args) {
        MyTest x = new MyTest();
        x.speak();
        x.say();
        x.fuck();
    }
}
class MyTest implements MyInterface2, MyInterface3 {
    @Override
    public void speak() {
        System.out.println("MyTest Called => jump() =>"+MyInterface.hello);
    }
    @Override
    public void fuck() {
        System.out.println("MyTest Called => fuck()");
    }
    @Override
    public void say() {
        System.out.println("MyTest Called => say()");
    }    
}
interface MyInterface1{
    public String hello = "hello";
    public void speak();
}
interface MyInterface2{
    public int num = 1;
    public void fuck();
}
// 接口之间可以相互继承
interface MyInterface3 extends MyInterface1{
    public void say();
}

输出如下:

$javac InterFace.java
$java InterFace

MyTest Called => jump() =>hello
MyTest Called => say()
MyTest Called => fuck()

这里我们声明了3个接口,并且interface3继承自interface1,所以当类容器导入接口interface3就会导入父类接口interface1。

只要添加了容器implements,就会包含接口中的所有东西,所以必须在MyTest类中添加该重写函数,否则找不到该函数会报错。

再看下面一个例子,多个类共同使用一个interface接口,保存为Account.java

interface Transaction {
    int BALANCE = 500;
    Object transaction(Object input);
}
class CurrentAccount implements Transaction {
    int bal;
    public Object transaction(Object input) {
        this.bal = BALANCE - (int)input;
        return bal;
    }
    public String toString() { return "Current acc"; }
}
class SavingsAccount implements Transaction {
    int bal;
    public Object transaction(Object input) {
        this.bal = BALANCE + (int)input;
        return bal;
    }
    public String toString() { return "Savings acc"; }
}
public class Account {
    public static void payment(Transaction t, Object input) {
        System.out.println(t + " is debited:   " +  t.transaction(input));
    }
    public static void deposit(Transaction t, Object input) {
        System.out.println(t + " is credited:   " +  t.transaction(input));
    }
    public static void main(String[] args) {
        Integer input = new Integer(600);
        deposit(new SavingsAccount(), input);
        payment(new CurrentAccount(), input);
    }
}

代码输出:

$javac Account.java
$java Account

Savings acc is credited:   1100
Current acc is debited:   -100

一个接口可以供多个类共同使用,并且多个类之间使用不冲突,这样看来,interface倒有点像是静态函数了。

观察一下这两个实现类活期账户和储蓄账户自动的向上转型在接受Transaction接口Account类中的方法。

payment()和deposit()方法利用我们所讲的战略设计模式,代表了接口的实现完全脱钩的一个实例。

从理论上说,你可以适应任何类,只需使它们符合的界面,使用这些方法。

对于接口与容器,我见过的一个更具有实用价值的地方,在于类之间的监听函数调用。

类似于js中的事件驱动函数,当有事件发生时候,通过回调函数,通知主函数。

实例代码如下,文件命名为Homeway.java:

public class Homeway {
    public static void main(String[] args) {
        System.out.println("
=======================Implements======================
");
        ClassImplements mClassImplements = new ClassImplements();
        mClassImplements.run();
    }
}
class ClassImplements implements Implements1.Listener {
    public Implements1 mImplements1 = null;
    public ClassImplements(){
        mImplements1 = new Implements1();
        mImplements1.setListener(this);
    }
    @Override
    public void onCallStart(){
        System.out.println("ClassImplements => onCallStart()");
    }
    @Override
    public void onCallStop(){
        System.out.println("ClassImplements => onCallStop()");
    }
    public void run(){
        mImplements1.run();
    }
}
//test 2level implements for class
class Implements1 implements Implements2.Listener {
    private Listener mListener;
    private Implements2 mImplements2;
    public Implements1(){
        mImplements2 = new Implements2();//把当前类传给下个类
        mImplements2.setListener(this);
        System.out.println("Init Implements1 =>...");
    }
    public static interface Listener {
        void onCallStart();
        void onCallStop();
    }
    public void setListener(Listener listener) {
        mListener = listener;
    }
    @Override
    public void onCallStart(){
        System.out.println("Implements1 => onCallStart()");
        mListener.onCallStart();//call at Implements1 and then throw to ClassImplements
    }
    @Override
    public void onCallStop(){
        System.out.println("Implements1 => onCallStop()");
        mListener.onCallStop();//call at Implements1 and then throw to ClassImplements
    }
    public void run(){
        this.mImplements2.run();
    }
}

//3 level implement test
class Implements2{
    private Listener mListener;
    public Implements2(){
        System.out.println("Init Implements2 =>...");
    }
    public static interface Listener {
        void onCallStart();
        void onCallStop();
    }
    public void setListener(Listener listener) {
        mListener = listener;
    }
    public void onCallStart(){
        System.out.println("Implements2 => onCallStart()");
    }
    public void onCallStop(){
        System.out.println("Implements2 => onCallStop()");
    }
    public void run() {
        System.out.println("Run some functions and then callback from Listener...");
        mListener.onCallStart();
        mListener.onCallStop();
    }

}

输出如下:

$javac Homeway.java
$java Homeway
=======================Implements======================
Init Implements2 =>...
Init Implements1 =>...
Run some functions and then callback from Listener...
Implements1 => onCallStart()
ClassImplements => onCallStart()
Implements1 => onCallStop()
ClassImplements => onCallStop()

我们先是声明了类ClassImplements,这个是我们的主类,并且implements了Implements1.Listener通过一个Listener建立了监听接口,

然后Implements1又implements了Implements2.Listener建立了第2级的监听。

一旦Implements1Implements2内的某个函数触发了某个事件,就能通过监听接口发送给主函数ClassImplements,类似js中的事件回调函数。

父类与子类通过Listener实现接口调用,此时Listener即为父类本身。

大致的模型如下:

implements容器与interface接口在java类中有很多很好用的模型,有时间该多去研究研究。


参考资料:

《Java Interfaces》

《Java interfaces and the concept of multiple inheritance》

《Java Interface Example, Explanation, and Implementation》

本文出自 夏日小草,转载请注明出处: http://homeway.me/2015/04/13/java-implements-and-interface/ by 小草 2015-04-13 20:10:20

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/64316.html

相关文章

  • java编程思想》—— 泛型

    摘要:引用泛型除了方法因不能使用外部实例参数外,其他继承实现成员变量,成员方法,方法返回值等都可使用。因此,生成的字节码仅包含普通的类,接口和方法。 为什么要使用泛型程序设计? 一般的类和方法,只能使用具体的类型:要么是基本类型,要么是自定义类的对应类型;如果要编写可以应用于多种类型的代码,这种刻板的限制对代码的束缚就会很大。----摘自原书Ordinary classes and meth...

    CODING 评论0 收藏0
  • Java编程思想》笔记9.接口

    摘要:抽象类和抽象方法抽象方法这种方法是不完整的,仅有声明而没有方法。创建抽象类和抽象方法非常有用,因为他们可以使累的抽象性明确起来,并告诉用户和编译器打算怎样来使用它们。接口用于建立类于类之间的协议。与抽象类相同,防止客户端程序员创建该类对象。 点击进入我的博客 接口和内部类为我们提供了一种将接口与实现分离的更加结构化的方法。 9.1抽象类和抽象方法 抽象方法:这种方法是不完整的,仅有...

    JessYanCoding 评论0 收藏0
  • 设计模式享元模式

    摘要:类图相关的设计模式享元模式和代理模式当代理模式消耗性能比较大的时候,就可以用享元模式享元模式和单例模式容器单例,享元模式就是复用对象的思想。源码中的享元模式源码地址享元模式参考慕课网设计模式精讲设计模式读书笔记享元模式 0x01.定义与类型 定义:提供了减少对象数量从而改善应用所需的对象结构的方法,系统使用少量对象,而且这些都比较相似,状态变化小,可以实现对象的多次复用。 运用共享技...

    vvpale 评论0 收藏0
  • 慕课网_《模式的秘密工厂模式》学习总结

    摘要:时间年月日星期日说明本文部分内容均来自慕课网。这对所有形态的工厂模式都是重要的这个系统的产品有至少一个的产品族同属于一个产品族的产品是设计成在一起使用的。 时间:2017年08月27日星期日说明:本文部分内容均来自慕课网。@慕课网:http://www.imooc.com教学源码:https://github.com/zccodere/s...学习源码:https://github.c...

    jsyzchen 评论0 收藏0
  • Java 学习笔记

    摘要:参考资料程序设计北大唐大仕零基础学语言浙大翁恺面向对象程序设计语言浙大翁恺在里面搜索可以查看和修改快捷键自动补全代码格式化简介历史与一起发展万维网所有信息用链接连接起来静态网页动态网页的出现年开发工具包语法增加广泛动态编译脚本 参考资料 Java程序设计 - 北大 - 唐大仕 零基础学Java语言 - 浙大 - 翁恺 面向对象程序设计——Java语言 - 浙大 - 翁恺 Ecl...

    tianlai 评论0 收藏0

发表评论

0条评论

MockingBird

|高级讲师

TA的文章

阅读更多
最新活动
阅读需要支付1元查看
<