迭代器模式实验(含答案)

合集下载

浙大JAVA实验题答案

浙大JAVA实验题答案

实验8 Method的使用1.程序填空题,不要改变与输入输出有关的语句;50001输入一个正整数repeat 0<repeat<10,做repeat次下列运算:输入1 个正整数n,计算 s 的前n项的和保留 4 位小数;s = 1 + 1/2 +....+ 1/n要求定义并调用函数factn计算n的阶乘;例:括号内是说明输入:2 repeat=22 n=210 n=10输出:public class Test50001 {public static void mainString args {int ri,repeat;int i,n;double s;Scanner in=new Scanner;repeat=;forri=1;ri<=repeat;ri++{n=;/-----------/s=0;for i=1;i<=n;i++s+=fact i;}}/---------------/static double fact int n {int i;double f=1;for i=1;i<=n;i++f=i;return f;}}50002输入一个正整数repeat 0<repeat<10,做repeat次下列运算:输入2个正整数a和n, 求a+aa+aaa+aa…an个a之和;要求定义并调用函数fna,n,它的功能是返回aa…an个a;例如,fn3,2的返回值是33;例:括号内是说明输入2 repeat=22 3 a=2, n=38 5 a=8, n=5输出246 2+22+22298760 8+88+888+8888+88888imponner;public class Test50002{public static void mainString args{int ri, repeat;int i, n,a;long sn;Scanner in=new Scanner;repeat=;forri=1; ri<=repeat; ri++{a=;n=;/------------/sn=0;for i=1;i<=n;i++sn+=fn a,i;}}/------------/s tatic int fn int a,int n{int s=0;forint i=1;i<=n;i++s=s10+a;return s;}}50003输入一个正整数repeat 0<repeat<10,做repeat次下列运算:读入1 个整数,统计并输出该数中2的个数;要求定义并调用函数countdigitnumber,digit,它的功能是统计整数number中数字digit的个数;例如,countdigit10090,0的返回值是3;例:括号内是说明输入:3 repeat=3-219022345543输出:count=2 -21902中有2个2count=1 有1个2count=0 345543中没有2public class Test50003{public static void mainString args{int ri, repeat;int count;long n;Scanner in=new Scanner;repeat=;forri=1; ri<=repeat; ri++{n=;/---------/n=n;count=countdigit n,2;}}/------------/static int countdigit long number,int digit{....要求定义并调用函数fibn,它的功能是返回第n项Fibonacci数;例如,fib7的返回值是13;例:括号内是说明输入:3 repeat=31 10 m=1, n=1020 100 m=20, n=1001000 6000 m=1000, n=6000输出:1 123 5 8 1到10之间的Fibonacci数21 34 55 89 20到100之间的Fibonacci数1597 2584 4181 1000到6000之间的Fibonacci数public class Test50006{public static void mainString args{int ri,repeat;int i, m, n;long f;Scanner in=new Scanner;repeat=;forri=1; ri<=repeat; ri++{m=;n=;/---------/i=1;f=1;while f<=n{if f>=m " ";i++;f=fib i;}}}/------------/sta ti c long fib int n{ //返回第n项Fibonacci数int i;long a=1,b=1,f=1;for i=3;i<=n;i++{ //从第3项开始计算f=a+b;a=b;b=f;}return f;}}50007输入一个正整数repeat 0<repeat<10,做repeat次下列运算:输入2 个正整数m和n1<=m,n<=10000,输出m 到n之间的所有完数完数就是因子和与它本身相等的数;要求定义并调用函数factorsumnumber,它的功能是返回number的因子和;例如,factorsum12的返回值是161+2+3+4+6;例:括号内是说明输入:2 repeat=220 500 m=100, n=4001 100 m=1, n=100输出:28 4961 6 28public class Test50007{public static void mainString args{int ri,repeat;int i, m, n;Scanner in=new Scanner;repeat=;forri=1;ri<=repeat;ri++{m=;n=;/---------/for i=m;i<=n;i++if i==factorsum i" ";}}/---------/static int factorsum int number{ //返回number的因子和int sum=0;if number==1sum=1;forint i=1;i<=number-1;i++if number%i==0sum+=i;return sum;}}50008输入一个正整数repeat 0<repeat<10,做repeat次下列运算:输入2 个正整数m和n1<=m,n<=1000,输出m 到n之间的所有满足各位数字的立方和等于它本身的数;要求定义并调用函数isnumber判断number的各位数字之立方和是否等于它本身;例:括号内是说明输入:2 repeat=2100 400 m=100, n=4001 100 m=1, n=100输出:153 370 371 111+555+333=153; 333+777=370; 333+777+111=3711public class Test50008{public static void mainString args{int ri,repeat;int i, m, n;Scanner in=new Scanner;repeat=;forri=1;ri<=repeat;ri++{m=;n=;/---------/for i=m;i<=n;i++if is i" ";}}/---------///判断number的各位数字之立方和是否等于它本身static boolean is int number{int sum=0,n,digit;n=number;while n>0{digit=n%10;n=n/10;sum+=digitdigitdigit;}if number==sum return true;else return false;}}50009输入一个正整数repeat 0<repeat<10,做repeat次下列运算:输入一个整数,将它逆序输出;要求定义并调用函数reversenumber,它的功能是返回number的逆序数;例如reverse12345的返回值是54321;例:括号内是说明输入4 repeat=4123456 -100 -2 99输出654321-1-299public class Test50009{public static void mainString args{int ri,repeat;long n, res;Scanner in=new Scanner;repeat=;forri=1;ri<=repeat;ri++{n=;/---------/res=reverse n;}}/---------/static long reverse long number{//返回number的逆序数int flag=1;long a=0,digit;if number<0{flag=-1;number=-number;}while number>0{digit=number%10; //分离出个位数字a=a10+digit; //形成当前的逆序数number=number/10;}return flaga;}}50011输入一个正整数repeat 0<repeat<10,做repeat次下列运算:输入三个整数a、b和c,输出其中较大的数;要求定义和调用函数maxa, b, c找出a、b中较大的数,函数形参a、b和c的类型是int;输入输出示例:括号内是说明输入3 repeat=3输入:5 8 9 a=5, b=8-1 -10 -5 a=-1, b=-101 1 1 a=1, b=1输出:max5,8,9=9max-1,-10,-5=-1max1,1,1=1public class Test50011 {public static void mainString args {int ri, repeat;int a,b,c,maximun;Scanner in = new Scanner;repeat = ;for ri = 1; ri <= repeat; ri++ {a = ;b = ;c=;/-----------------/maximun=maximuna,b,c;Sy}}/-------------------/static int maximunint a,int b,int c{int max=a;ifmax<bmax=b;ifmax<cmax=c;return max;}}。

浙大JAVA 实验题答案05answer1

浙大JAVA 实验题答案05answer1

实验5 分支结构程序的设计1.程序填空题,不要改变与输入输出有关的语句。

20004 计算旅途时间输入2个整数time1和time2,表示火车的出发时间和到达时间,计算并输出旅途时间。

有效的时间范围是0000到2359,不需要考虑出发时间晚于到达时间的情况。

例:括号内是说明输入712 1411(出发时间是7:12,到达时间是14:11)输出The train journey time is 6 hrs 59 mins.import java.util.Scanner;public class Test20004 {public static void main(String[] args) {Scanner in=new Scanner(System.in);int time1, time2, hours, mins;time1=in.nextInt();time2=in.nextInt();/*------------------*//*计算两个时间之间的小时数和分钟数*/hours=time2/100-time1/100;mins=time2%100-time1%100;/*当计算得到的分钟数为负数时进行调整*/hours=mins>0?hours:hours-1;mins=mins>0?mins:mins+60;//或:if(mins<0){hours-=1;mins+=60;}System.out.println("The train journey time is "+hours+" hrs "+ mins+" mins.");}}30001 显示两级成绩输入一个正整数repeat (0<repeat<10),做repeat次下列运算:输入一个学生的数学成绩,如果它低于60,输出“Fail”,否则,输出“Pass”。

2021高中信息技术Python操作考试题(6套含答案)

2021高中信息技术Python操作考试题(6套含答案)

2021高中信息技术Python操作考试题(6套含答案)本文档包含了2021年高中信息技术Python操作考试题的六套试卷以及答案。

以下是每套试卷的简要概述:试卷一题目一请编写一个Python程序,要求用户输入一个整数,然后输出该整数的平方。

题目二请编写一个Python程序,要求用户输入一个字符串,然后输出该字符串的长度。

题目三请编写一个Python程序,要求用户输入一个列表,然后输出列表中的最大值和最小值。

题目四请编写一个Python程序,要求用户输入一个正整数,然后判断该数是否为质数,并输出判断结果。

题目五请编写一个Python程序,要求用户输入一个字符串,然后将字符串按照字母顺序进行排序,并输出排序后的结果。

答案题目一的答案:[代码实现]num = int(input("请输入一个整数:"))result = num ** 2print("该整数的平方是:", result)题目二的答案:[代码实现]string = input("请输入一个字符串:")length = len(string)print("该字符串的长度是:", length)题目三的答案:[代码实现]lst = input("请输入一个列表(以空格分隔各个元素):").split() lst = list(map(int, lst))max_value = max(lst)min_value = min(lst)print("该列表的最大值是:", max_value)print("该列表的最小值是:", min_value)题目四的答案:[代码实现]num = int(input("请输入一个正整数:"))is_prime = Truefor i in range(2, num):if num % i == 0:is_prime = Falsebreakif is_prime:print(num, "是质数")else:print(num, "不是质数")题目五的答案:[代码实现]string = input("请输入一个字符串:")sorted_string = ''.join(sorted(string))print("排序后的字符串是:", sorted_string)试卷二题目一请编写一个Python程序,要求用户输入一个正整数n,然后输出1到n之间所有偶数的和。

Iterator与Iterable(迭代器模式)

Iterator与Iterable(迭代器模式)

Iterator与Iterable(迭代器模式)1、引⾔在Java中,我们可以对List集合进⾏如下⼏种⽅式的遍历:List<Integer> list = new ArrayList<>();// 法⼀:普通for循环for (int i = 0; i < list.size(); i++) {System.out.print(list.get(i) + ",");}//法⼆:迭代器遍历Iterator it = list.iterator();while (it.hasNext()) {System.out.print(it.next() + ",");}// for each遍历for (Integer i : list) {System.out.print(i + ",");}// 后⾯两种⽅式涉及到Java中的Iterator和Iterable对象2、两者关系看Iterable和Iterator所处包位置,Collection接⼝必须继承ng.Iterable接⼝。

Iterator为Java中的迭代器对象,是能够对List这样的集合进⾏迭代遍历的底层依赖。

Iterable接⼝⾥定义了返回Iterator的⽅法,相当于对Iterator的封装,同时实现了Iterable接⼝的类可以⽀持for each循环。

JDK中 Iterator 接⼝源码:public interface Iterator<E> {boolean hasNext(); // 检查序列中是否还有元素E next(); // 获取序列中下⼀个元素default void remove() { // 将迭代器新返回的元素删除throw new UnsupportedOperationException("remove");}// 1.8新增的Iterator接⼝中的默认⽅法,对集合中*剩余*的元素进⾏操作,直到元素完毕或者抛出异常;注意为“剩余”,即迭代中还剩余的部分 default void forEachRemaining(Consumer<? super E> action) {Objects.requireNonNull(action);while (hasNext())action.accept(next());}}集合类都实现了这个接⼝, Iterator 是迭代器最简单的实现,使⽤Iterator iter = list.iterator()就实现了迭代器(见上⾯引⾔的使⽤)Iterable接⼝的源码:public interface Iterable<T> {Iterator<T> iterator(); // ⽅法iterator()返回了⼀个Iterator对象(各具体类返回的类型也不同)// 1.8新加的⽅法,对每个元素执⾏特有操作,可使⽤Lambda表达式default void forEach(Consumer<? super T> action) {Objects.requireNonNull(action);for (T t : this) {action.accept(t);}}// 1.8新⽅法,可分割迭代器,⽤于并⾏遍历元素default Spliterator<T> spliterator() {return Spliterators.spliteratorUnknownSize(iterator(), 0);}}for each实现:为Java语法糖,也是依赖Iterator迭代器,编译器⾃动转化for (Integer i : list);for(Iterator iterator = list.iterator(); iterator.hasNext(); System.out.println(i)){i = (Integer)iterator.next();}3、为什么这样设计这⾥是使⽤到了设计模式中的迭代器模式为什么⽤Iterator实现遍历?(为什么使⽤迭代器模式)⽤于遍历集合类的标准访问⽅法,它可以把访问逻辑从不同类型的集合类中抽象出来,从⽽避免向客户端暴露集合的内部结构(其他索引遍历需要知道集合内部结构,且更换集合时需要重写遍历⽅法);⽀持以不同的⽅式遍历⼀个聚合对象;简化了聚合类;在同⼀个聚合上可以有多个遍历;便于增加迭代器类和新的聚合类。

奥鹏东北大学21年12月考试软件设计模式X考核作业 参考答案

奥鹏东北大学21年12月考试软件设计模式X考核作业 参考答案

东北大学继续教育学院软件设计模式X 试卷(作业考核线上2) A 卷(共7 页)1.常用的基本设计模式可分为(A)A.创建型、结构型和行为型B.对象型、结构型和行为型C.过程型、结构型和行为型D.抽象型、接口型和实现型2.对以下开闭原则的描述错误的是(A)A.开闭原则与“对可变性的封装原则”没有相似性B.找到个系统的可变元素,将它封装起来,叫开闭原则C.对修改关闭,是其原则之一D.从抽象层导出一个或多个新具体类可以改变系统的行为,是其原则之一3. “不要和陌生人说话”是(D)原则的通俗表述。

A.接口隔离B.里氏替换C.依赖倒置D.迪米特4.当创建一个具体的对象而又不希望指定具体的类时,可以使用(D)A.结构型B.创建型C.行为型D.以上都可以5.以下(O是利用一个对象,快速地生成一批对象。

A.抽象工厂(AbStraCt Factory)模式B.原型(PrototyPe)模式C.合成(COmPOSite)模式D.桥接(Bridge)模式6.以下(B )用来描述建造者(Builder )。

A.定义一个用于创建对象的接口,让子类决定实例化哪一个类B.将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示C.保证一个类仅有一个实例,并提供一个访问它的全周访问点D.运用共享技术有效地支持大量细粒度的对象7.以下(C )用来描述工厂方法(Factory Method)模式。

A.提供一个创建一系列相关或相互依赖对象的接口,而无须指定它们具体的类8.表示一个作用于某对象结构中的各元素的操作。

它使用户可以在不改变各元素的类的前提下定义作用于这些元素的新操作C.定义一个用于创建对象的接口,让子类决定实例化哪一个类。

该模式使一个类的实例化延迟到其子类D.定义一系列的算法,把它们一个个封装起来,并且使它们可相互替换。

本模式使得算法可独立于使用它的客户而变化8.对象适配器模式是(A )原则的典型应用。

A.将一个类的接口转换成客户希望的另外一个接口,本模式使原本由于接口不兼容而不能一起工作的那些类可以一起工作。

python二级考试试题4及答案

python二级考试试题4及答案

python二级考试试题4及答案1. 题目:请解释Python中的列表推导式,并给出一个使用列表推导式生成一个包含1到10的平方数的列表的示例代码。

答案:列表推导式是Python中的一种简洁的构建列表的方法,它允许开发者通过一个表达式来创建列表。

列表推导式通常用于从旧的列表中创建新的列表,或者通过一定的条件筛选元素。

以下是一个使用列表推导式生成1到10的平方数列表的示例代码:```pythonsquares = [x2 for x in range(1, 11)]```2. 题目:描述Python中装饰器的作用,并提供一个简单的装饰器示例。

答案:装饰器是Python中一个非常重要的概念,它允许用户在不修改原有函数代码的情况下,增加函数的额外功能。

装饰器本质上是一个函数,它接受一个函数作为参数并返回一个新的函数。

以下是一个简单的装饰器示例,该装饰器用于打印函数执行前后的时间:```pythonimport timedef timer(func):def wrapper(*args, kwargs):start_time = time.time()result = func(*args, kwargs)end_time = time.time()print(f"Function {func.__name__} took {end_time - start_time} seconds to execute.")return resultreturn wrapper@timerdef example_function():time.sleep(2)print("Function executed.")```3. 题目:解释Python中的生成器是什么,并提供一个生成器函数的示例。

答案:生成器是Python中一种特殊的迭代器,它允许开发者使用更少的内存来处理大型数据集。

C#设计模式系列:迭代器模式(Iterator)

C#设计模式系列:迭代器模式(Iterator)

C#设计模式系列:迭代器模式(Iterator) 迭代器模式把对象的职责分离,职责分离可以最⼤限度减少彼此之间的耦合程度,从⽽建⽴⼀个松耦合的对象。

职责分离的要点是对被分离的职责进⾏封装,并以抽象的⽅式建⽴彼此之间的关系。

1、迭代器模式简介1.1>、定义 迭代器模式提供⼀种⽅法可以顺序访问聚合对象中各个元素,但⼜不暴露该对象的内部表⽰。

1.2>、使⽤频率 ⾼2、迭代器模式结构2.1>、结构图2.2>、参与者 迭代器模式参与者: ◊ Iterator:迭代器定义访问和遍历元素的接⼝ ◊ ConcreteIterator ° 具体迭代器实现迭代器接⼝ ° 对该聚合遍历时跟踪当前位置 ◊ Aggregate:聚合定义创建Iterator对象的接⼝ ◊ ConcreteAggregate:具体聚合,实现相应迭代器的接⼝,返回具体迭代器的⼀个适当的实例。

在迭代器模式中,ConcreteAggregate通过Aggregate定义的接⼝得到Iterator,并且这是⼀个ConcreteIterator,该ConcreteIterator具体实现了对ConcreteAggregate的访问与遍历的⽅法。

通过ConcreteIterator可以访问并使⽤集合中的元素。

3、迭代器模式结构实现 Iterator.csusing System;using System.Collections.Generic;using System.Linq;using System.Text;namespace DesignPatterns.IteratorPattern.Structural{public abstract class Iterator{public abstract object First();public abstract object Next();public abstract bool IsDone();public abstract object CurrentItem();}} Aggregate.csusing System;using System.Collections.Generic;using System.Linq;using System.Text;namespace DesignPatterns.IteratorPattern.Structural{public abstract class Aggregate{public abstract Iterator CreateIterator();}} ConcreteAggregate.csusing System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Collections;namespace DesignPatterns.IteratorPattern.Structural{public class ConcreteAggregate : Aggregate{private ArrayList _items = new ArrayList();public override Iterator CreateIterator(){return new ConcreteIterator(this);}public int Count{get { return _items.Count; }}public object this[int index]{get { return _items[index]; }set { _items.Insert(index, value); }}}} ConcreteIterator.csusing System;using System.Collections.Generic;using System.Linq;using System.Text;namespace DesignPatterns.IteratorPattern.Structural{public class ConcreteIterator : Iterator{private ConcreteAggregate _aggregate;private int _current = 0;public ConcreteIterator(ConcreteAggregate aggregate) {this._aggregate = aggregate;}public override object First(){return _aggregate[0];}public override object Next(){object ret = null;if (_current < _aggregate.Count - 1){ret = _aggregate[++_current];}return ret;}public override object CurrentItem(){return _aggregate[_current];}public override bool IsDone(){return _current >= _aggregate.Count;}}} Program.csusing System;using System.Collections.Generic;using System.Linq;using System.Text;using DesignPatterns.IteratorPattern.Structural;namespace DesignPatterns.IteratorPattern{class Program{static void Main(string[] args){ConcreteAggregate a = new ConcreteAggregate();a[0] = "Item A";a[1] = "Item B";a[2] = "Item C";a[3] = "Item D";ConcreteIterator i = new ConcreteIterator(a);Console.WriteLine("Iterating over collection:");object item = i.First();while (item != null){Console.WriteLine(item);item = i.Next();}}}} 运⾏输出:Iterating over collection:Item AItem BItem CItem D请按任意键继续. . .4、迭代器模式实践应⽤ 在迭代器模式的设计中,有两种具体的实现⽅式,分别为外禀迭代器和内禀迭代器。

raptor实验参考答案

raptor实验参考答案

raptor实验参考答案Raptor实验参考答案在计算机科学领域,Raptor是一种流程图工具,用于可视化算法和程序的设计过程。

它提供了一种直观和简洁的方式来描述和分析问题,并通过图形化表示来帮助程序员更好地理解和编写代码。

在学习和教学中,Raptor经常被用于教授算法和程序设计的基本概念。

本文将提供一些Raptor实验的参考答案,希望能对初学者有所帮助。

实验一:计算两个数的和算法描述:1. 输入两个整数num1和num2;2. 计算它们的和sum = num1 + num2;3. 输出sum。

Raptor流程图:```输入 num1输入 num2sum = num1 + num2输出 sum```实验二:计算斐波那契数列算法描述:1. 输入一个正整数n;2. 初始化变量a和b为0和1;3. 循环n次,每次计算a和b的和,并将结果赋给a,将b的值赋给a;4. 输出a作为斐波那契数列的第n项。

Raptor流程图:```输入 na = 0b = 1循环 n 次temp = aa = a + bb = temp输出 a```实验三:查找数组中的最大值算法描述:1. 输入一个整数数组arr;2. 初始化变量max为数组的第一个元素arr[0];3. 遍历数组,如果当前元素大于max,则将其赋给max;4. 输出max作为数组的最大值。

Raptor流程图:```输入 arrmax = arr[0]遍历数组如果 arr[i] > maxmax = arr[i]输出 max```实验四:判断一个数是否为素数算法描述:1. 输入一个正整数num;2. 初始化变量isPrime为true;3. 循环遍历从2到num的所有数字,如果存在能整除num的数字,则将isPrime置为false;4. 输出isPrime作为num是否为素数的判断结果。

Raptor流程图:```输入 numisPrime = true循环遍历 2 到 num如果 num 能被当前数字整除isPrime = false输出 isPrime```通过以上实验参考答案,我们可以看到Raptor作为一种流程图工具,能够帮助我们更好地理解和设计算法和程序。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

课程名称:软件体系结构与设计迭代器(Iterator)模式实验一、实验目的1. 掌握迭代器模式的概念;2. 掌握迭代器模式的功能;3. 加深对迭代器模式的了解;4. 提高对迭代器模式的运用;5. 将该模式运用但实际的生活中。

二、实验内容1. 阅读和查看资料了解迭代器模式的概念和功能;2. 将有关代理模式的迭代器模式理解透彻并运行;3. 举例说明生活中的一个可以使用迭代器模式的例子;4. 熟悉迭代器模式的扩展,迭代器模式是比较有用途的一种模式,而且变种较多,应用场合覆盖从小结构到整个系统的大结构。

三、实验环境Windows7 、Java虚拟机、MyEclipse 环境下运行代码。

四、实验设计原理迭代器(Iterator)模式,又叫做游标(Cursor)模式。

它提供一种方法顺序访问一个聚合对象(或容器对象:container)中各个元素, 而又不需暴露该对象的内部。

聚合:表示一组对象的组合结构,比如JAVA中的数组,集合等从定义可见,迭代器模式是为容器而生。

很明显,对容器对象的访问必然涉及到遍历算法。

你可以一股脑的将遍历方法塞到容器对象中去;或者根本不去提供什么遍历算法,让使用容器的人自己去实现去吧。

这两种情况好像都能够解决问题。

然而在前一种情况,容器承受了过多的功能,它不仅要负责自己“容器”内的元素维护(添加、删除等等),而且还要提供遍历自身的接口;而且由于遍历状态保存的问题,不能对同一个容器对象同时进行多个遍历。

第二种方式倒是省事,却又将容器的内部细节暴露无遗。

而迭代器模式的出现,很好的解决了上面两种情况的弊端。

迭代器模式的类图如下图所示:类图解读:从结构上可以看出,迭代器模式在客户与容器之间加入了迭代器角色。

迭代器角色的加入,就可以很好的避免容器内部细节的暴露,而且也使得设计符号“单一职责原则”。

注意,在迭代器模式中,具体迭代器角色和具体容器角色是耦合在一起的——遍历算法是与容器的内部细节紧密相关的。

为了使客户程序从与具体迭代器角色耦合的困境中脱离出来,避免具体迭代器角色的更换给客户程序带来的修改,迭代器模式抽象了具体迭代器角色,使得客户程序更具一般性和重用性。

这被称为多态迭代。

迭代器模式所涉及的角色有:参与者:•迭代器角色(Iterator):定义访问和遍历元素的接口。

•具体迭代器角色(Concrete Iterator):关联到被迭代的具体聚集对象角色,继承迭代器角色实现具体的迭代,并负责管理记录遍历中的当前位置。

•聚集对象抽象角色(Aggregate):负责提供创建具体迭代器角色的接口。

•具体聚集对象角色(Concrete Aggreate):持有一个对象的集合,实现创建具体迭代器角色的接口,返回集合遍历所依赖的一个迭代器。

●一个迭代器模式例子:●20世纪80年代的黑白电视机,没有遥控器,每次开关机或者换台都需要通过电视机上面的那些按钮来完成,如果你想换台的话,需要亲自用手去旋转换台的按钮,每转一下就“啪”的响一声,如果没有收到任何电视频道就会出现一片让人眼花的雪花点。

还要移动电视机上面那两根可以前后左右移动变长变短的天线。

随着科技的飞速发展,越来越高级的电视机相继出现,那种古老的电视机几乎看不到了。

与那时的电视机相比,现今的电视机给我们带来的最大便利之一就是增加了电视机遥控器,我们在进行开机、关机、换台、改变音量等操作时都无须直接操作电视机,可以通过遥控器来间接实现。

我们可以将电视机看成一个存储电视频道的集合对象,通过遥控器可以对电视机中的电视频道集合进行操作,如返回上一个频道、跳转到下一个频道或者跳转至指定的频道。

遥控器为我们操作电视频道带来很大的方便,用户并不需要知道这些频道到底如何存储在电视机中。

电视机遥控器和电视机示意图如图1所示:●●在软件开发中,也存在大量类似电视机一样的类,它们可以存储多个成员对象(元素),这些类通常称为聚合类(Aggregate Classes),对应的对象称为聚合对象。

为了更加方便地操作这些聚合对象,同时可以很灵活地为聚合对象增加不同的遍历方法,我们也需要类似电视机遥控器一样的角色,可以访问一个聚合对象中的元素但又不需要暴露它的内部结构。

本章我们将要学习的迭代器模式将为聚合对象提供一个遥控器,通过引入迭代器,客户端无须了解聚合对象的内部结构即可实现对聚合对象中成员的遍历,还可以根据需要很方便地增加新的遍历方式。

●迭代器模式的作用:●迭代器模式能够遍历一组聚合对象,不需要了解其内部结构还能提供不同的遍历方法。

●就是分离了集合对象的遍历行为,将遍历算法交给这个迭代器角色来完成,可以很好的避免容器内部细节的暴露,而且也使得设计符合“单一职责原则”,另外迭代器模式抽象了具体迭代器角色,可以通过对一个抽象迭代器多个集成可来完成同一聚集对象的多种遍历。

五、迭代器模式示例性代码首先有一个抽象的聚集,所谓的聚集就是就是数据的集合,可以循环去访问它。

它只有一个方法GetIterator()让子类去实现,用来获得一个迭代器对象。

1///<summary>23///抽象聚集45///</summary>67public interface IList89 {10 IIterator GetIterator();11 }抽象的迭代器,它是用来访问聚集的类,封装了一些方法,用来把聚集中的数据按顺序读取出来。

通常会有MoveNext()、CurrentItem()、Fisrt()、Next()等几个方法让子类去实现。

1///<summary>23///抽象迭代器45///</summary>67public interface IIterator8 {9bool MoveNext();1011 Object CurrentItem();13void First();1415void Next();16 }具体的聚集,它实现了抽象聚集中的唯一的方法,同时在里面保存了一组数据,这里我们加上Length属性和GetElement()方法是为了便于访问聚集中的数据。

1///<summary>23///具体聚集45///</summary>67public class ConcreteList : IList8 {9int[] list;1011public ConcreteList()1213 {14 list = new int[] { 1,2,3,4,5};15 }17public IIterator GetIterator()1819 {20return new ConcreteIterator(this);21 }2223public int Length2425 {26get { return list.Length; }27 }2829public int GetElement(int index)3031 {32return list[index];33 }34 }具体迭代器,实现了抽象迭代器中的四个方法,在它的构造函数中需要接受一个具体聚集类型的参数,在这里面我们可以根据实际的情况去编写不同的迭代方式。

1/**////<summary>23///具体迭代器45///</summary>67public class ConcreteIterator : IIterator89 {10private ConcreteList list;1112private int index;1314public ConcreteIterator(ConcreteList list) 1516 {17this.list = list;1819 index = 0;20 }2122public bool MoveNext()2324 {25if (index < list.Length)2627return true;2829else3031return false;32 }3334public Object CurrentItem()3536 {37return list.GetElement(index) ;38 }3940public void First()4142 {43 index = 0;44 }46public void Next()4748 {49if (index < list.Length)5051 {52 index++;53 }54 }55 }简单的客户端程序调用:1/**////<summary>23///客户端程序45///</summary>67class Program89 {10static void Main(string[] args)12 {13 IIterator iterator;1415 IList list = new ConcreteList();1617 iterator = list.GetIterator();1819while (iterator.MoveNext())2021 {22int i = (int)iterator.CurrentItem();23 Console.WriteLine(i.ToString()); 2425 iterator.Next();26 }2728 Console.Read();2930 }3132 }Iterator实现要点:1.迭代抽象:访问一个聚合对象的内容而无需暴露它的内部表示。

2.迭代多态:为遍历不同的集合结构提供一个统一的接口,从而支持同样的算法在不同的集合结构上进行操作。

3.迭代器的健壮性考虑:遍历的同时更改迭代器所在的集合结构,会导致问题。

题目:假设某软件公司Z为某超市开发了一套销售管理系统,在对该系统进行分析和设计时,Z公司开发人员发现经常需要对系统中的商品数据、客户数据等进行遍历,为了复用这些遍历代码,Z公司开发人员设计了一个抽象的数据聚合类AbstractObjectList,而将存储商品和客户登记的类作为其子类。

AbstractObjectList类结构如下图所示。

在上图中,IList类型的对象objects用于存储数据,AbstractObjectList类的方法说明如下表所示:AbstractObjectList类的子类ProductList和CustomerList分别用于存储商品数据和客户数据。

请用迭代器模式编程实现。

代码:import java.util.*;//抽象聚合类abstract class AbstractObjectList {protected List<Object> objects = new ArrayList<Object>();}public void addObject(Object obj) {this.objects.add(obj);}public void removeObject(Object obj) {this.objects.remove(obj);}return this.objects;}//声明创建迭代器对象的抽象工厂方法public abstract AbstractIterator createIterator(); }//商品数据类:具体聚合类class ProductList extends AbstractObjectList {super(products);}//实现创建迭代器对象的具体工厂方法public AbstractIterator createIterator() {return new ProductIterator(this);}}//客户数据类:具体聚合类class CustomerList extends AbstractObjectList {super(customers);}//实现创建迭代器对象的具体工厂方法public AbstractIterator createIterator() {return new CustomerIterator(this);}}//抽象迭代器interface AbstractIterator {public void next(); //移至下一个元素public boolean isLast(); //判断是否为最后一个元素public void previous(); //移至上一个元素public boolean isFirst(); //判断是否为第一个元素public Object getNextItem(); //获取下一个元素public Object getPreviousItem(); //获取上一个元素}//商品迭代器:具体迭代器class ProductIterator implements AbstractIterator {private int cursor1; //定义一个游标,用于记录正向遍历的位置private int cursor2; //定义一个游标,用于记录逆向遍历的位置public ProductIterator(ProductList list) {this.productList = list;this.products = list.getObjects(); //获取集合对象cursor1 = 0; //设置正向遍历游标的初始值cursor2 = products.size() -1; //设置逆向遍历游标的初始值}public void next() {if(cursor1 < products.size()) {cursor1++;}}public boolean isLast() {return (cursor1 == products.size());}public void previous() {if (cursor2 > -1) {cursor2--;}}public boolean isFirst() {return (cursor2 == -1);}public Object getNextItem() {return products.get(cursor1);}public Object getPreviousItem() {return products.get(cursor2);}}//客户迭代器:具体迭代器class CustomerIterator implements AbstractIterator {private int cursor1; //定义一个游标,用于记录正向遍历的位置private int cursor2; //定义一个游标,用于记录逆向遍历的位置public CustomerIterator(CustomerList list) {this.customerList = list;this.customers = list.getObjects(); //获取集合对象cursor1 = 0; //设置正向遍历游标的初始值cursor2 = customers.size() -1; //设置逆向遍历游标的初始值}public void next() {if(cursor1 < customers.size()) {cursor1++;}}public boolean isLast() {return (cursor1 == customers.size());}public void previous() {if (cursor2 > -1) {cursor2--;}}public boolean isFirst() {return (cursor2 == -1);}public Object getNextItem() {return customers.get(cursor1);}public Object getPreviousItem() {return customers.get(cursor2);}}public class Iterator {public static void main(String args[]) {List<String> products = new ArrayList<String>();products.add("农夫山泉");products.add("百岁山");products.add("康师傅");products.add("旺仔");products.add("统一");AbstractObjectList list;AbstractIterator iterator;list = new ProductList(products); //创建聚合对象iterator = list.createIterator(); //创建迭代器对象System.out.println("***************商品数据***************");System.out.println("正向遍历:");while(!iterator.isLast()) {System.out.print(iterator.getNextItem() + ",");iterator.next();}System.out.println();System.out.println("逆向遍历:");while(!iterator.isFirst()) {System.out.print(iterator.getPreviousItem() + ",");iterator.previous();}List<String> customers = new ArrayList<String>(); customers.add("张三");customers.add("李四");customers.add("王五");customers.add("赵六");AbstractObjectList list1;AbstractIterator iterator1;list1 = new ProductList(customers); //创建聚合对象iterator1 = list1.createIterator(); //创建迭代器对象System.out.println();System.out.println("***************客户数据***************");System.out.println("正向遍历:");while(!iterator1.isLast()) {System.out.print(iterator1.getNextItem() + ",");iterator1.next();}System.out.println();System.out.println("逆向遍历:");while(!iterator1.isFirst()) {System.out.print(iterator1.getPreviousItem() + ",");iterator1.previous();}}}。

相关文档
最新文档