Head First 设计模式 —— 10. 迭代器 (Iterator) 模式
思考题
public void printMenu() {
PancakeHouseMenu pancakeHouseMenu = new PancakeHouseMenu();
ArrayList breakfastItems = pancakeHouseMenu.getMenuItems();
DinerMenu dinerMenu = new DinerMenu();
MenuItem[] lunchItems = dinerMenu.getMenuItems();
for (int i = 0; i < breakfastItems.size(); ++i) {
MenuItem menuItem = (MenuItem) breakfastItems.get(i);
System.out.print(menuItem.getName() + " ");
System.out.println(menuItem.getPrice() + " ");
System.out.println(menuItem.getDescription());
}
for (int i = 0; i < lunchItems.length; ++i) {
MenuItem menuItem = lunchItems[i];
System.out.print(menuItem.getName() + " ");
System.out.println(menuItem.getPrice() + " ");
System.out.println(menuItem.getDescription());
}
}
根据我们的 printMenu()
实现,下列哪一项为真? P322
- [x] A. 我们是针对
PancakeHouseMenu
和DinerMenu
的具体实现编码,而不是针对接口。- 针对具体实现编程,没有解耦,无法动态替换
- [ ] B. 女招待没有实现 Java 招待 API ,所以她没有遵守标准。
- 女招待有一个招待规格,算是实现了一个隐式 API,并且内部实现封装了变化
- [x] C. 如果我们决定从
DinerMenu
切换到另一种菜单,此菜单的项是用Hashtable
来存放的,我们会因此需要修改女招待中的许多代码。Hashtable
是一种新的具体实现,需要修改代码进行适配
- [x] D. 女招待需要知道每个菜单如何表达内部的菜单项集合,这违反了封装。
- 女招待的实现依赖菜单内部实现,与菜单强耦合,没有封装变化
- [x] E. 我们有重复的代码;
printMenu()
方法需要两个循环,来遍历两种不同的菜单。如果我们加上第三种菜单,我们就需要第三个循环。- 由于是针对菜单项集合的具体实现编程,所以增加新菜单就需要增加循环
- [ ] F. 这个实现并没有基于 MXML(Menu XML),所以就没有办法互操作。
The implementation isn't based on MXML(Menu XML) and so isn't as interoperable as it shoule be.
互操作性(英文:Interoperability;中文又称为:协同工作能力,互用性)作为一种特性,它指的是不同的系统和组织机构之间相互合作,协同工作(即互操作)的能力。就软件而言,互操作性——这条术语用来描述的是不同的程序(programs)借助于同一套交换格式(exchange formats)来交换数据,读写相同文件格式(file formats)以及采用相同协议(protocols)的能力。
刚开始不懂,看了维基百科后的解释后有点似懂非懂。这个实现内部直接处理了不同数据格式,具有一定的互操作性。
思考题
请继续完成 PancakeHouseIterator
的实现,并对 PancakeHouseMenu
类做出必要的修改。 P327
public class PancakeHouseIterator implements Iterator {
ArrayList items;
int position = 0;
public PancakeHouseIterator(ArrayList items) {
this.items = items;
}
public Object next() {
return items.get(position++);
}
public boolean hasNext() {
return position >= items.size();
}
}
public class PancakeHouseMenu {
ArrayList menuItems;
// 构造器和其他方法
// 移除 public ArrayList getMenuItems() 方法
public Iterator createIterator() {
return new PancakeHouseIterator(menuItems);
}
}
迭代器模式
提供一种方法顺序访问一个聚合对象中的各个元素,而又不暴露其内部的表示。 P336
特点
- 遍历集合内部元素而不暴露内部表示
P336
- 让聚合的接口和实现变得简洁
P336
- 管理对象集合,不必理会遍历的事情
P336
思考题
迭代器模式的类图看起来很像我们所学过的另一个模式;你知道是哪个模式吗?提示:子类决定要创建哪个对象。 P337
- 工厂方法模式
设计原则
单一职责原则:一个类应该只有一个引起变化的原因 P339
- 高内聚:一个模块或一个类只支持一组相关的功能
P339
特点
- 尽量将一个责任只指派给一个类
P339
- 遵循单一职责原则的类是高内聚的
P339
思考题
请很快写下为了能让咖啡厅的菜单代码符合我们的框架,我们要对它做的三件事情: P342
public class CafeMenu {
HashTable menuItems = new Hashtable();
public CafeMenu() {
// 省略下述参数
// addItem(...);
// addItem(...);
// addItem(...);
}
public void addItem(String name, String description, boolean vegetarian, double price) {
MenuItem menuItem = new MenuItem(name, description, vegetarian, price);
menuItems.put(menuItem.getName(), menuItem);
}
public Hashtable getItems() {
return menuItems;
}
}
- 实现
Menu
接口 - 删除
getItems()
方法 - 增加
createIterator()
方法
本文首发于公众号:满赋诸机(点击查看原文) 开源在 GitHub :reading-notes/head-first-design-patterns
Head First 设计模式 —— 10. 迭代器 (Iterator) 模式的更多相关文章
- 1、迭代器 Iterator模式 一个一个遍历 行为型设计模式
1.Iterator模式 迭代器(iterator)有时又称游标(cursor)是程序设计的软件设计模式,可在容器(container,例如链表或者阵列)上遍访的接口,设计人员无需关心容器的内容. I ...
- 【设计模式大法】Iterator模式
Iterator模式 --一个一个遍历 在Java中的for语句中 i++的作用是让 i 的值在每次循环后自增1,这样就可以访问数组中的下一个元素.下下一个元素.再下下一个元素,也就实现了从头至尾逐一 ...
- Java 实现迭代器(Iterator)模式
类图 /** * 自己定义集合接口, 相似java.util.Collection * 用于数据存储 * @author stone * */ public interface ICollection ...
- 设计模式—迭代器Iterator模式
什么是迭代器模式? 让用户通过特定的接口访问容器的数据,不需要了解容器内部的数据结构. 首先我们先模仿集合中ArrayList和LinkedList的实现.一个是基于数组的实现.一个是基于链表的实现, ...
- 设计模式C++描述----20.迭代器(Iterator)模式
一. 举例说明 我们知道,在 STL 里提供 Iterator 来遍历 Vector 或者 List 数据结构. Iterator 模式也正是用来解决对一个聚合对象的遍历问题,将对聚合的遍历封装到一个 ...
- 设计模式——迭代器(Iterator)模式
概述 迭代器模式简单的说(按我目前的理解)就是一个类提供一个对外迭代的接口,方面调用者迭代.这个迭代接口至少包括两个方法:hasNext()--用于判断是否还有下一个,next()--用于取出下一个对 ...
- GoLang设计模式10 - 中介者模式
中介者模式是一种行为型设计模式.在中介者模式中创建了一个中介对象来负责不同类间的通信.因为这些类不需要直接交互,所以也就能避免它们之间的直接依赖,实现解耦的效果. 中介者模式的一个典型案例是老式小火车 ...
- JS常用的设计模式(10)——模版方法模式
模式方法是预先定义一组算法,先把算法的不变部分抽象到父类,再将另外一些可变的步骤延迟到子类去实现.听起来有点像工厂模式( 非前面说过的简单工厂模式 ). 最大的区别是,工厂模式的意图是根据子类的实现最 ...
- 设计模式(10)--Facade(外观模式)--结构型
作者QQ:1095737364 QQ群:123300273 欢迎加入! 1.模式定义: 外观模式提供了一个统一的接口,用来访问子系统中的一群接口.外观定义了一个高层接口,让子系统更容易使 ...
随机推荐
- AcWing 345. 牛站 Cow Relays
由于我太菜了,不会矩阵乘法,所以给同样不会矩阵乘法同学的福利 首先发现这题点很多边很少,实际上有用的点 \(<= 2 * T\)(因为每条边会触及两个点嘛) 所以我们可以把点的范围缩到 \(2 ...
- mysql扩展百分位函数(类似SUM)
mysql扩展百分位函数(类似SUM) 参考:https://my.oschina.net/waterbear/blog/1186744 百度搜索:mysql percentile
- Hexo博客框架10分钟搭建个人博客
首先是先给大家打个招呼 最近看网上看到了很多的的关于搭建博客的视频,我自己也学着自己搭建了一个博客"我自己的博客链接"(欢迎大家来我的博客跟我深入交♂流),今天我把搭建的过程记录下 ...
- java-01-基础语法
1. 注释 单行注释 格式: // 注释信息 多行注释 格式: /* 注释信息 */ 文档注释 格式: /** 注释信息 */ 2. 常量 定义:在程序运行过程中,其值不可发生改变的量 分类: 常量类 ...
- Kafka Producer TimeoutException
基本需求 程序读取HDFS上的日志发送至Kafka集群 由于日志量较大 每小时约7亿条+ 采用多线程 多producer实例发送 TPS 可达到120W+ 修改前Producer配置 val prop ...
- js下 Day12、案例
一.垃圾分类 效果图: 功能思路分析: 1. 鼠标按下 (1) 获取鼠标到元素的距离(e.offsetX) (2) 开启开关变量 (3) 获取事件源 (4) 记录垃圾初始位置 2. 鼠标移动 ( ...
- Redis 基础知识点总结
关系型数据库 VS 非关系型数据库(NoSQL) 关系型数据库 我们过去使用的 mysql.Oracle 都属于关系型数据库.关系型数据库的特点是数据表之间可以存在联系,表内每列数据也存在关联,同时支 ...
- 关于MySQL索引知识与小妙招 — get get get
一.索引基本知识 1.1 索引的优点 大大减少了服务器需要扫描的数据量,加快数据库的检索速度 帮助服务器避免排序和临时表 将随机io变成顺序io 1.2 索引的用处 速查找匹配WHERE子句的行 从c ...
- 不一样的资产安全 3D 可视化平台
前言 数字经济时代,应用好数据是企业数字化转型的关键,基于前沿科学技术进行数据的有效管控,更是对数字增值服务的新趋势.近年来,整个安全行业对资产管理的重视程度正在提高.据IDC发布的相关数据显示, ...
- Autofac的基本使用---3、泛型类型
Autofac的基本使用---目录 准备 使用的表是Teacher,创建相关的IDAL.DAL.IBLL.BLL层. 使用EF,创建一个Model层,存放edmx文件. 创建一个Infrastruct ...