C#实现迭代器
Posted 小小架构师
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C#实现迭代器相关的知识,希望对你有一定的参考价值。
迭代器模式(Iterator),提供一种方法顺序访问一个聚合对象中的各种元素,而又不暴露该对象的内部表示。C#中使用
IEnumerator
接口实现,Java中使用
Iterator
接口实现,其中原理都差不多,下面我就用C#代码来演示下迭代器的实现。
假如我要实现一个自定义容器列表,就叫它
SpecialList
吧,可以实现类似
ArrayList
的功能。如下:
这个时候我想遍历这个列表,当我使用
foreach
的时候,报错了。如下:
提示
SpecialList
不包含
GetEnumerator
的公共实例定义,在C#中,如果想要使用foreach遍历列表对象,这个列表对象必须要实现
IEnumerable
的Get
Enumerator()
方法,我们来加一下。如下:
继承后,
foreach
列表的时候就不会再报错了,但我们并没有实现
GetEnumerator()
这个方法。我们看一下这个方法的返回值类型为
IEumerator
,F12进去看一下这个接口的定义。如下:
这个接口里面有两个方法和一个属性。其中
MoveNext()
是最核心的方法,就是在这个里面实现列表的遍历。话不多说,我们先定义一个继承
IEnumerator
的类,就叫
SpecialEnumerator
吧。如下:
不好意思,我已经简单的写好这个类了,那就简单的讲一个这个类的原理吧。
SpecialEnumerator
主要定义了一个
SpecialList
类型的
_list
,还有当前元素的
_current
,还有当前索引的
_index
。我们重点看一下
MoveNext
方法,里面的代码其实也非常简单,就是判断_index是否已经到底,没有的话叫取出当前_index上的元素赋予
_cuurent
,然后返回true,这里的返回值给到
foreach
,如果为true,则继续遍历,如果为false,则
foreach
跳出循环。我们再来看一下
SpecialList
中怎么使用
SpecialEnumerator
类。如下:
这样只是返回
SpecialEnumerator
的一个实例,同时将当前要枚举的列表对象(this)传入进去。你可能会有疑问,这里只是返回一个对象,在
foreach
中并没有循环判断
MoveNext
是true还是false的代码,那它是怎么实现的呢?其实
foreach
只是一个语法糖,它本质上其实是使用了
while
语法来实现的。如下:
到这里,相信大家已经明白迭代器是怎么实现的了。最后再补充一下,大家可能会觉得额外实现
SpecialEnumerator
类比较繁琐,其实如果你的列表遍历规则比较简单的话,可以使用
yield
语法来代替
SpecialEnumerator
类,只要这样写就行。如下:
但如果你的列表遍历规则比较特殊,比如像栈、队列这样的容器类时,还是建议实现枚举类,这样可以将遍历规则封装在
MoveNext
中。
以上是关于C#实现迭代器的主要内容,如果未能解决你的问题,请参考以下文章
从C#走进Python迭代器
通过Lua迭代器自定义实现对c#集合的遍历
C#实现迭代器
C#迭代器实现
C# 自定义迭代器实现
C# Iterator迭代器的实现方式