Java接口 详解(二)
上一篇Java接口 详解(一)讲到了接口的基本概念、接口的使用和接口的实际应用(标准定义)。我们接着来讲。
一、接口的应用—工厂设计模式(Factory)
我们先看一个范例:
package com.wz.factoryDemo;
interface Fruit{
public void eat();
}
class Apple implements Fruit{
@Override
public void eat() {
System.out.println("吃苹果。。。");
}
}
public class Client {
public static void main(String[] args) {
Fruit f = new Apple();
f.eat();
}
}
运行结果:
吃苹果。。。
以上程序非常简单,就是通过接口的子类为接口对象实例化,但这样操作会存在什么样的问题呢?在软件开发中,我们强调以下两点:
(1)主方法或主类是一个客户端,客户端的操作应该越简单越好;
(2)客户端之外的代码修改,不影响用户的使用。也就是说,用户可以不用去关心代码是否由变更。
确实,以上范例没有任何语法错误,但关键的问题是客户端中出现的new关键字上。因为,一个接口会有多个子类,对于上面的Furit接口,也可能出现多个子类对象。
来看范例,我们多加上一个接口子类:
class Orange implements Fruit{
@Override
public void eat() {
System.out.println("吃橘子。。。");
}
}
客户端是若要得到这个新的子类对象,需要修改代码为:
public class Client {
public static void main(String[] args) {
//Fruit f = new Apple();
Fruit f = new Orange();
f.eat();
}
}
从上面我们发现,如果直接在客户端上产生一个实例化对象,那么我们每次要更换对象时,都需要修改客户端代码,这样的做法明显是不好的。而在整个代码中,我们最关心的是如何取得一个Fruit接口对象,然后进行方法的调用,至于这个接口对象时被谁实例化的,不是客户端关心的。这个问题就是代码耦合度太高!耦合度太高的产生的直接问题是代码不方便维护。
在本程序之中,最大的问题在于耦合上,发现在主方法中,一个接口和一个子类紧密耦合在一起,这种方式比较直接,可以简单的理解为由A —>B,但是这种紧密的方式不方便于维护,所以我们可以这样改:A—> C—>B,中间经历了一个过渡,这样一来,B改变,然后C去改变,但是A不需要改变。这可以参考Java中JVM的设计思想:程序—> JVM—>适应不同的操作系统。
于是,本程序我们这么修改,加上一个工厂类:
class Factory{
public static Fruit getInstance(String className){
if("apple".equals(className)){
return new Apple();
}else if("orange".equals(className)){
return new Orange();
}else{
return null;
}
}
}
然后修改客户端:
public class Client {
public static void main(String[] args) {
Fruit f = Factory.getInstance("apple");
f.eat();
}
}
运行结果:
吃苹果。。。
这样的话,客户端不会看见具体的子类,客户端不再和一个具体的子类耦合在一起了,就算以后增加了新的子类,那么只需要修改Factory类即可实现,客户端的调用不会改变。
工厂模式的关系图如下:
从工厂模式关系图看出,客户端不和具体的子类耦合在一起,若要增加新的子类,只需要修改Factory类即可实现。
二、接口的应用—代理设计模式(Proxy)
Java代理设计模式单独讲解,请移步到Java设计模式之代理模式
所谓代理,就是一个人或者机构代表另一个人或者机构采取行动。在一些情况下,一个客户不想或者不能够直接引用一个对象,而代理对象可以在客户端和目标对象之间起到中介的作用。
关系图如下:
代理设计模式的核心精髓就在于:有一个主题操作接口(接口中可能有多个方法),而核心业务主题只完成核心功能,而代理主题负责完成所有与核心主题有关的辅助性操作。
三、Java抽象类和接口的区别
通过上面的分析可以得出结论:在开发之中,抽象类和接口实际上都是可以使用的,并且使用那一个都没有明确的限制,可是抽象类有一个最大的缺点 : 一个子类只能够继承一个抽象类,存在单继承的局限。所以当遇到抽象类和接口都可以使用的情况下,优先考虑接口,避免单继承局限。
一些参考原则(根据自身情况参考):
(1)在进行某些公共操作的时候一定要定义出接口;
(2)有了接口就需要利用子类完善方法;
(3)如果是我们自己写的接口,尽量不要使用关键字new去直接实例化接口子类,要使用工厂类完成。
Java接口 详解(二)的更多相关文章
- Java多线程详解(二)
评论区留下邮箱可获得<Java多线程设计模式详解> 转载请指明来源 1)后台线程 后台线程是为其他线程服务的一种线程,像JVM的垃圾回收线程就是一种后台线程.后台线程总是等到非后台线程死亡 ...
- java 接口详解
定义接口 接口继承和实现继承的规则不同,一个类只有一个直接父类,但可以实现多个接口.Java 接口本身没有任何实现,只描述 public 行为,因此 Java 接口比 Java 抽象类更抽象化.Jav ...
- Java接口 详解(一)
一.基本概念 接口(Interface),在JAVA编程语言中是一个抽象类型,是抽象方法的集合.接口通常以interface来声明.一个类通过继承接口的方式,从而来继承接口的抽象方法. 如果一个类只由 ...
- Java集合详解二
前一篇我们已经讲过了Collectin是存放单值的最大接口, 可以看到Map接口和其主要之类的关系图如下: 快速访问 HashMap HashTable TreeMap Map输出 那Map ...
- “全栈2019”Java第八十四章:接口中嵌套接口详解
难度 初级 学习时间 10分钟 适合人群 零基础 开发语言 Java 开发环境 JDK v11 IntelliJ IDEA v2018.3 文章原文链接 "全栈2019"Java第 ...
- “全栈2019”Java第八十三章:内部类与接口详解
难度 初级 学习时间 10分钟 适合人群 零基础 开发语言 Java 开发环境 JDK v11 IntelliJ IDEA v2018.3 文章原文链接 "全栈2019"Java第 ...
- Java Annotation详解(二): 反射和Annotation
前面一篇文<Java Annotation详解(一): 理解和使用Annotation>中,我们或许会觉得,Annotation注释其实并没有多大的作用,除了几个内建的Annotation ...
- Java内部类详解
Java内部类详解 说起内部类这个词,想必很多人都不陌生,但是又会觉得不熟悉.原因是平时编写代码时可能用到的场景不多,用得最多的是在有事件监听的情况下,并且即使用到也很少去总结内部类的用法.今天我们就 ...
- Java虚拟机详解----JVM常见问题总结
[声明] 欢迎转载,但请保留文章原始出处→_→ 生命壹号:http://www.cnblogs.com/smyhvae/ 文章来源:http://www.cnblogs.com/smyhvae/p/4 ...
随机推荐
- wordpress账户防暴力破解攻击
一.修改数据库表前缀 默认的表前缀是wp_,如果你安装博客的时候没有修改,可以参考这篇文章修改下表前缀. 修改完登录测试下,如果登录成功后提示“您没有足够的权限访问该页面”,说明前缀没有修改完整,参照 ...
- HDU 3657 Game(取数 最小割)经典
Game Time Limit: 4000/2000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total Submi ...
- storm笔记:Storm+Kafka简单应用
storm笔记:Storm+Kafka简单应用 这几天工作须要使用storm+kafka,基本场景是应用出现错误,发送日志到kafka的某个topic.storm订阅该topic.然后进行兴许处理.场 ...
- OC中动态创建可变数组的问题.有一个数组,数组中有13个元素,先将该数组进行分组,每3个元素为一组,分为若干组,最后用一个数组统一管理这些分组.(要动态创建数组).两种方法
<span style="font-size:24px;">//////第一种方法 // NSMutableArray *arr = [NSMutableArray a ...
- iOS多线程与网络开发之小文件上传
郝萌主倾心贡献,尊重作者的劳动成果,请勿转载. /** 取得本地文件的MIMEType */ 2 - (void) getMIMEType { 3 // Socket 实现断点上传 4 5 //apa ...
- Spring Cloud(十三):Spring Cloud Sleuth服务链路追踪(zipkin)(转)
这篇文章主要讲述服务追踪组件zipkin,Spring Cloud Sleuth集成了zipkin组件. 一.简介 Spring Cloud Sleuth 主要功能就是在分布式系统中提供追踪解决方案, ...
- 【转】AngularJs 弹出框 model(模态框)
原文转至 http://blog.csdn.net/violet_day/article/details/17170585 $modal是一个可以迅速创建模态窗口的服务,创建部分页,控制器,并关联他们 ...
- inflate, findViewById与setContentView的差别与联系
protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentV ...
- HP Vertica Analytics Platform 评測
1.vertica概念 面向数据分析的数据仓库系统解决方式 2.vertica关键特性 Ø 标准的SQL接口:能够利用已有的BI.ETL.Hadoop/MapReduce和OLTP环境 Ø 高可用 ...
- spring中xml配置和autowired混用
1.类的混用: 配置文件中的配置: <bean id="a" class="com.ab.cc.A" /> 类中的配置 @Autowired A a ...