Java设计模式(三)原型模型 适配器型号
(五岁以下儿童)原型模型 Prototype
样机模型旨在复制一个现有对象来创建新对象。而不是通过的方式的实例。原型模式须要实现 Cloneable 接口。覆写clone方法,复制分为浅复制、深复制。
浅复制:将一个对象复制后。基本数据类型的变量都又一次创建,引用类型。指向的还是原对象所指向的。
深复制:讲一个对象复制后。不论基本数据类型和引用类型,都是又一次创建。是全然的彻底的复制。
public class ProtoType {
public static void main(String[] args) throws Exception {
Father f=new Father();
User u1=new User("123456",f);
User u2=(User)u1.clone();
User u3=(User) u1.shallowClone();
System.out.println(u1==u2); //false
System.out.println(u1.f==u2.f); //false
System.out.println(u1.password == u2.password); //false
System.out.println(u1.f==u3.f); //true
System.out.println(u1.password == u3.password); //true
}
}
class User implements Cloneable,Serializable{
String password;
Father f;
public User(String password,Father f){
this.password=password;
this.f=f;
}
//浅复制
public Object shallowClone() throws CloneNotSupportedException{
User user = (User)super.clone();
return user;
}
//深复制
public Object clone() throws CloneNotSupportedException {
//return super.clone();
ObjectOutputStream out=null;
ObjectInputStream in=null;
try {
ByteArrayOutputStream bo = new ByteArrayOutputStream();
out = new ObjectOutputStream(bo);
out.writeObject(this);
out.flush();
byte[] bs = bo.toByteArray();
ByteArrayInputStream bi = new ByteArrayInputStream(bs);
in = new ObjectInputStream(bi);
Object o = in.readObject();
return o;
} catch (IOException e) {
e.printStackTrace();
return null;
} catch (ClassNotFoundException e) {
e.printStackTrace();
return null;
}
finally{
try {
out.close();
in.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
class Father implements Serializable{}
原型模式与调用构造函数相比,复制创建的新对象会包括原始对象的某些状态,尤其当多个对象的类在属性上存在细微区别,方法全然同样时候。
浅复制与深复制还存在一个问题就是引用类型成本的问题。对于代码来说就是 Father 值的问题。上面的代码改动下。
class Father implements Serializable{
String name = "father";
}
public static void main(String[] args) throws Exception {
Father f = new Father();
User u1 = new User("123456",f);
User u2 = (User)u1.clone();
User u3 = (User) u1.shallowClone();
u1.f.name = "aaaa";
System.out.println(u1.f.name); //aaaa 原型
System.out.println(u2.f.name); //father 深复制
System.out.println(u3.f.name); //aaaa 浅复制
}
这样应该能跟深刻的理解了。
(六)适配器模式
适配器的意义在于,使用不同接口的类所提供的服务为client提供它所期望的接口。原类型不做不论什么改变。用一个适配器把一个接口转成还有一个接口,扩展了新的接口。适配器是面向对象的精髓。适配器模式主要分为三类:类的适配器模式、对象的适配器模式、接口的适配器模式。
类的适配器模式:
Source类。拥有一个方法。待适配,目标接口 Targetable 。通过 Adapter 类将source的功能扩展到 targetable 。
class Source{
public void method1(){
System.out.println("this is original method!");
}
}
interface Targetable{
//原类中的方法
public void method1();
//新类中的方法
public void method2();
}
class Adapter extends Source implements Targetable{
//能够覆写Source的方法。也能够删去method1.会调用Source的
public void method1() {
super.method1();
System.out.println("targetable method1");
}
public void method2() {
System.out.println("targetable method2");
}
}
public class AdapterTest {
public static void main(String[] args) {
Targetable target = new Adapter();
target.method1();
target.method2();
}
}
对象的适配器模式:
跟类的适配器模式基本同样,仅仅是不继承Source 类,持有Source类的实例。
class Adapter implements Targetable{// extends Source implements Targetable{
private Source source;
public Adapter(Source source){
super();
this.source = source;
}
//能够覆写Source的方法。也能够删去method1.会调用Source的
public void method1() {
source.method1();
System.out.println("targetable method1");
}
public void method2() {
System.out.println("targetable method2");
}
}
public class AdapterTest {
public static void main(String[] args) {
Source source = new Source();
Adapter target = new Adapter(source);
target.method1();
target.method2();
}
}
接口适配器:
接口适配器跟前两种有点差别。一个接口会有多个抽象方法,我们写接口的实现类的时候,必须实现该接口全部的方法,可是并非全部方法都是我们须要的,为了解决问题。我们引入了接口适配器。借助于一个抽象类,改抽象类实现了上面的接口,并实现了全部的方法。而我们不和原始的接口打交道,仅仅和该抽象类取得联系。
我们最后写一个类,继承该抽象类。重写我们须要的方法。
interface Sourceable{
public void method1();
public void method2();
}
abstract class Wrapper implements Sourceable{
//父类或者子类必须有一个实现method1 跟method2接口
public void method1(){System.out.println("Wrapper method1");}
public void method2(){System.out.println("Wrapper method2");}
}
class SourceSub1 extends Wrapper{
//由于父类已经实现了method2所以不会报错
public void method1(){
System.out.println("SourceSub1");
}
}
class SourceSub2 extends Wrapper{
public void method2(){
System.out.println("SourceSub2");
}
}
public class AdapterInterface {
public static void main(String[] args){
SourceSub1 source1 = new SourceSub1();
SourceSub2 source2 = new SourceSub2();
source1.method1(); //SourceSub1
source1.method2(); //Wrapper method2
source2.method1(); //Wrapper method1
source2.method2(); //SourceSub2
}
}
版权声明:本文博客原创文章,博客,未经同意,不得转载。
Java设计模式(三)原型模型 适配器型号的更多相关文章
- java设计模式4——原型模式
java设计模式4--原型模式 1.写在前面 本节内容与C++语言的复制构造函数.浅拷贝.深拷贝极为相似,因此建议学习者可以先了解C++的该部分的相关知识,或者学习完本节内容后,也去了解C++的相应内 ...
- JAVA 设计模式之原型模式
目录 JAVA 设计模式之原型模式 简介 Java实现 1.浅拷贝 2.深拷贝 优缺点说明 1.优点 2.缺点 JAVA 设计模式之原型模式 简介 原型模式是六种创建型设计模式之一,主要应用于创建相同 ...
- 孙悟空的身外身法术使用了Java设计模式:原型模式
目录 定义 意图 主要解决问题 何时使用 优缺点 结构 简单形式的原型模式 登记形式的原型模式 两种形式比较 浅克隆和深克隆 孙悟空的身外身法术 浅克隆实现 深克隆实现 定义 原型模式属于对象的创建型 ...
- java设计模式之原型模式
原型模式概念 该模式的思想就是将一个对象作为原型,对其进行复制.克隆,产生一个和原对象类似的新对象.java中复制通过clone()实现的.clone中涉及深.浅复制.深.浅复制的概念如下: ⑴浅复制 ...
- [译]Java 设计模式之原型
(文章翻译自Java Design Pattern: Prototype) 原型模式用于当当非常相似的对象频繁被需要的时候.原型模式克隆了对象并且设置变化的特征.这种方式会消耗更少的资源.考虑下为什么 ...
- JAVA设计模式之 原型模式【Prototype Pattern】
一.概述: 使用原型实例指定创建对象的种类,而且通过拷贝这些原型创建新的对象. 简单的说就是对象的拷贝生成新的对象(对象的克隆),原型模式是一种对象创建型模式. 二.使用场景: 创建新的对象能够通过对 ...
- java设计模式之五原型模式(Prototype)
原型模式虽然是创建型的模式,但是与工程模式没有关系,从名字即可看出,该模式的思想就是将一个对象作为原型,对其进行复制.克隆,产生一个和原对象类似的新对象.本小结会通过对象的复制,进行讲解.在Java中 ...
- Java设计模式透析之 —— 适配器(Adapter)
转载请注明出处:http://blog.csdn.net/sinyu890807/article/details/9400141 今天一大早,你的leader就匆匆忙忙跑过来找到你:“快,快,紧急任务 ...
- java设计模式---三种工厂模式之间的区别
简单工厂,工厂方法,抽象工厂都属于设计模式中的创建型模式.其主要功能都是帮助我们把对象的实例化部分抽取了出来,优化了系统的架构,并且增强了系统的扩展性. 本文是本人对这三种模式学习后的一个小结以及对他 ...
随机推荐
- Oracle的海量存储技术
下午去參加一个Oracle有关海量数据存储技术的培训讲座了. 地址在广州市林和西路101号天河区计经大楼西側三楼. 培训发起机构为:广州中睿信息技术有限公司. 以下就简要总结一下所听到的一些东西,也算 ...
- 查看.a架构文件
苹果公司现在要求所有新提交的评论app,我们必须支持64位架构.而我们的在线项目编制,操作员做了一堆SDK在需要访问,我们发现,在这个过程中,有些SDK的.a文件进入后,链接错误,如提示 Undefi ...
- 【C语言探索之旅】 第二部分第一课:模块化编程
内容简介 1.课程大纲 2.第二部分第一课: 模块化编程 3.第二部分第二课预告: 进击的指针,C语言王牌 课程大纲 我们的课程分为四大部分,每一个部分结束后都会有练习题,并会公布答案.还会带大家用C ...
- 发现SQL Server惊天大秘密!!
原文:发现SQL Server惊天大秘密!! --set statistics xml onCREATE TABLE T_TEST(ID INT IDENTITY PRIMARY KEY,Create ...
- 华为-on演习--身高找到最好的二人
称号: 从5个人选择2作为个人礼仪器.中的每个个体的身高的范围160-190,要求2各高度差值至少(假设差异值同样的事情,他们中最高的选择),输出的两个人的身高升序. Smple input:161 ...
- 编程算法 - 数字数组中只出现一次 代码(C)
数字数组中只出现一次 代码(C) 本文地址: http://blog.csdn.net/caroline_wendy 题目: 一个整型数组里除了两个数字以外, 其它的数字都出现了两次. 请敲代码找出这 ...
- MEF初体验之十二:Composition Batch
一个MEF容器实例是不可变的.如果catalog支持改变(像观察一个目录的改变)或是如果你的代码在运行时添加或移除部件,改变都可能发生.以前,你不得不作出改变并在组合容器上调用它的组合方法.在Prev ...
- SpringMVC源代码深度分析DispatcherServlet核心的控制器(初始化)
SpringMVC是非常优秀的MVC框架,每一个框架都是为了我们提高开发效率,我们试图通过对SpringMVC的源码去了解这个框架,了解整个设计思想,框架要有扩展性,这里用的比較多是接口和抽象,是框架 ...
- 采用shell脚本统计代码的行数
刚毕业那会儿有一次去台湾公司面试,我问多行代码怎么写.我从来没有想过这个问题,粗略计算,.惊叹:大概几十万行不行. 最近整理资料,看着eclipse左边全面上市,我觉得这个东西.代码共同拥有的行倒底总 ...
- 《TCP/IP具体解释》读书笔记(18章)-TCP连接的建立与中止
TCP是一个面向连接的协议.不管哪一方向还有一方发送数据之前.都必须在两方之间建立一条连接.这样的两端间连接的建立与无连接协议UDP不同.UDP向还有一端发送数据报时,无需不论什么预告的握手. 1.建 ...