共计 3082 个字符,预计需要花费 8 分钟才能阅读完成。
导读 | 本文详细讲解了 C# 中的 yield 关键字,文中通过示例代码介绍的非常详细。对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下 |
在 ”C# 中, 什么时候用 yield return” 中,我们了解到:使用 yield return 返回集合,不是一次性加载到内存中,而是客户端每调用一次就返回一个集合元素,是一种 ” 按需供给 ”。本篇来重温 yield return 的用法,探秘 yield 背后的故事并自定义一个能达到 yield return 相同效果的类,最后体验 yield break 的用法。
以下代码创建一个集合并遍历集合。
class Program
{static Random r = new Random();
static IEnumerable GetList(int count)
{List list = new List ();
for (int i = 0; i
使用 yield return 也能获得同样的结果。修改 GetList 方法为:
static IEnumerable GetList(int count)
{for (int i = 0; i
通过断点调试发现:客户端每显示一个集合中的元素,都会到 GetList 方法去获取集合元素。
使用 yield return 获取集合,并遍历。
class Program
{public static Random r = new Random();
static IEnumerable GetList(int count)
{for (int i = 0; i
生成项目,并用 Reflector 反编译可执行文件。在.NET 1.0 版本下查看 GetList 方法,发现该方法返回的是一个 GetList 类的实例。原来 yield return 是 ” 语法糖 ”,其本质是生成了一个 GetList 的实例。
那 GetList 实例是什么呢?点击 Reflector 中
接下来,就模拟 GetList,我们自定义一个 GetRandomNumbersClass 类,使之能达到 yield return 相同的效果。
using System;
using System.Collections;
using System.Collections.Generic;
namespace ConsoleApplication2
{
class Program
{public static Random r = new Random();
static IEnumerable GetList(int count)
{GetRandomNumbersClass ret = new GetRandomNumbersClass();
ret.count = count;
return ret;
}
static void Main(string[] args)
{foreach(int item in GetList(5))
Console.WriteLine(item);
Console.ReadKey();}
}
class GetRandomNumbersClass : IEnumerable , IEnumerator
{
public int count;// 集合元素的数量
public int i; // 当前指针
private int current;// 存储当前值
private int state;// 保存遍历的状态
#region 实现 IEnumerator 接口
public int Current
{get { return current;}
}
public bool MoveNext()
{switch (state)
{
case 0: // 即为初始默认值
i = 0;// 把指针调向 0
goto case 1;
break;
case 1:
state = 1;// 先设置原状态
if (!(i GetEnumerator()
{return this;}
// 被显式调用的属性
IEnumerator IEnumerable.GetEnumerator()
{return GetEnumerator();
}
#endregion
}
}
关于 GetRandomNumbersClass 类:
迭代器的 MoveNext 方法是关键:
如此循环
假设在一个无限循环的环境中获取一个 int 类型的集合,在客户端通过某个条件来终止循环。
class Program
{static Random rand = new Random();
static IEnumerable GetList()
{while (true)
{yield return rand.Next(100);
}
}
static void Main(string[] args)
{foreach (int item in GetList())
{if (item%10 == 0)
{break;}
Console.WriteLine(item);
}
Console.ReadKey();}
}
以上,当集合元素可以被 10 整除的时候,就终止循环。终止循环的时机是在循环遍历的时候。
如果用 yield break, 就可以在获取集合的时候,当符合某种条件就终止获取集合。
class Program
{static Random rand = new Random();
static IEnumerable GetList()
{while (true)
{int temp = rand.Next(100);
if (temp%10 == 0)
{yield break;}
yield return temp;
}
}
static void Main(string[] args)
{foreach (int item in GetList())
{Console.WriteLine(item);
}
Console.ReadKey();}
}
以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值