第十八章
- IEnumerator接口:实现了IEnumerator接口的枚举器有三个函数成员:Current、MoveNext和Reset;Current返回当前位置的属性,它是只读属性;MoveNext前进位置到下一项,如果新的位置是有效的(没有到达序列尾部),返回true,否则返回false,并且在调用Current之前,先调用MoveNext(因为枚举器的原始位置在序列的第一项之前);Reset是把位置设置到原始状态。
(不完整代码,只是为了叙述理解而已)
static void Main()
{
int[] Myint = {10,12,14,16,18};
IEnumerator ie = Myint.GetEnumerator(); //获取枚举器
while(ie.MoveNext()) //移到下一项
{
int i = (int)ie.Current; //获取当前项
Console.WriteLine("{0}",i);
}
}
- IEnumerable接口:实现IEnumerable接口的类是可枚举类,该接口有一个函数成员——GetEnumerator方法,它返回对象的枚举器。
using System.Collections.Generic;
class Myclass:IEnumerable //实现IEnumerable接口
{
public IEnumerator GetEnumerator() //返回枚举器 IEnumerator 的对象
{
...
}
}
- 可枚举类的示例:
//可枚举类
using System;
using System.Collections;
namespace test38
{
class ColorEnumerator:IEnumerator //实现枚举器的三个方法
{
string[] _colors;
int _position = -1;
public ColorEnumerator(string[] theColors)
{
_colors = new string[theColors.Length];
for(int i = 0;i<theColors.Length;i++)
{
_colors[i] = theColors[i];
}
}
public object Current //属性
{
get
{
if((_position == -1)||(_position >=_colors.Length))
{
throw new InvalidOperationException();
}
return _colors[_position];
}
}
public bool MoveNext() //返回bool类型
{
if(_position <= _colors.Length -1)
{
_position ++;
return true;
}
else
return false;
}
public void Reset()
{
_position = -1;
}
}
class Spectrum:IEnumerable //可枚举类提供要枚举的内容
{
string[] Colors = {"violet","blue","cyan","green","yellow","orange","","red"};
public IEnumerator GetEnumerator() //返回枚举器
{
return new ColorEnumerator(Colors); //往枚举器中传入要枚举的内容
}
}
class Program
{
static void Main(string[] args)
{
Spectrum spectrums = new Spectrum();
foreach(string color in spectrums)
{
Console.WriteLine(color);
}
}
}
}
执行结果:
- 泛型与非泛型枚举接口:对于非泛型接口形式,IEnumerable接口的 GetEnumerator方法返回实现IEnumerator 枚举器的实例;实现IEnumerator 的类实现了Current属性,它返回object的引用,然后我们必须把它转化为实际类型的对象;对于泛型接口形式,IEnumerable的GetEnumerator方法返回实现IEnumerator的枚举器的实例;实现IEnumerator的类实现了Current属性,它返回实际类型的对象,而不是object基类的对象。
- 迭代器块:含有一个或者多个yield return 语句的代码块它可以是方法块的实体、运算符的实体和访问器的实体;yield return 指定在序列中返回的下一项,yield brake指定在序列中没有下一项;
- 使用迭代器创建枚举器和可枚举类:
using System;
using System.Collections;
namespace test39
{
class Myclass
{
//使用迭代器创建枚举器
public IEnumerator GetEnumerator() //返回枚举器
{
return BlackAndWhite();
}
public IEnumerator BlackAndWhite() //迭代器
{
yield return "black";
yield return "gray";
yield return "white";
}
}
//使用迭代器创建可枚举类型
class Myclass1
{
public IEnumerator GetEnumerator() //返回枚举器
{
IEnumerable myEnumerable = BlackAndWhite(); //将迭代器赋给可枚举类型的变量
return myEnumerable.GetEnumerator(); //获取枚举器,方法返回枚举器的实例
}
public IEnumerable BlackAndWhite() //迭代器,返回可枚举类型
{
yield return "black";
yield return "gray";
yield return "white";
}
}
class Program
{
static void Main(string[] args)
{
Console.WriteLine("使用迭代器创建枚举器");
Myclass mc = new Myclass();
foreach(string str in mc) //使用类对象
{
Console.WriteLine(str);
}
Console.WriteLine("使用迭代器创建可枚举类型");
Myclass1 mc1 = new Myclass1();
foreach(string str in mc1.BlackAndWhite()) //使用类枚举器方法
{
Console.WriteLine(str);
}
}
}
}
执行结果:
- 产生多个可枚举类型
using System;
using System.Collections.Generic;
namespace test40
{
class Spectrum
{
string[] Color = {"violet","blue","cyan","green","yellow","orange","red"};
public IEnumerable<string> UVtoIR() //自定义的方法需要使用泛型
{
for(int i = 0;i<Color.Length;i++)
{
yield return Color[i];
}
}
public IEnumerable<string> IRtoUV()
{
for(int i = Color.Length-1;i>= 0;i--)
{
yield return Color[i];
}
}
}
class Program
{
static void Main(string[] args)
{
Spectrum spectrum = new Spectrum();
Console.WriteLine("........正序打印颜色........");
foreach(string item in spectrum.UVtoIR())
{
Console.WriteLine(item);
}
Console.WriteLine("........倒序打印颜色........");
foreach(string item in spectrum.IRtoUV())
{
Console.WriteLine(item);
}
}
}
}
执行结果:
- 将迭代器作为属性
using System;
using System.Collections.Generic;
namespace test41
{
class Spectrum
{
bool _listFromUVtoIR;
string[] Color = {"violet","blue","cyan","green","yellow","orange","red"};
public Spectrum(bool listFromUVtoIR)
{
_listFromUVtoIR = listFromUVtoIR ;
}
public IEnumerator<string> GetEnumerator()
{
return _listFromUVtoIR?UVtoIR:IRtoUV;
}
public IEnumerator<string> UVtoIR
{
get
{
for(int i = 0;i<Color.Length;i++)
{
yield return Color[i];
}
}
}
public IEnumerator<string> IRtoUV
{
get
{
for(int i = Color.Length-1;i>= 0;i--)
{
yield return Color[i];
}
}
}
}
class Program
{
static void Main(string[] args)
{
Spectrum StartUV = new Spectrum(true);
Spectrum StartIR = new Spectrum(false);
Console.WriteLine("........正序打印颜色........");
foreach(string item in StartUV)
{
Console.WriteLine(item);
}
Console.WriteLine("........倒序打印颜色........");
foreach(string item in StartIR)
{
Console.WriteLine(item);
}
}
}
}
执行结果: