前言
yield关键字在c#中简化了数据迭代的方式,实现了按需生成数据,自动维护迭代状态,减少了内存占用,并允许在迭代时执行复杂逻辑。
传统迭代和yield迭代方式对比
咱们来看看传统迭代方式和yield关键字迭代方式对比,是否如传说中的代码实现起来更简洁和高效:
/// <summary>
/// 传统迭代方式和yield关键字迭代方式对比
/// </summary>
public static void iteratorcomparisonrun()
{
console.writeline("迭代器方法使用yield关键字:");
foreach (var number in getnumberswithyield())
{
console.writeline(number);
}
console.writeline("传统迭代方法返回一个list<int>");
var numbers = getnumberswithoutyield();
foreach (var number in numbers)
{
console.writeline(number);
}
}
/// <summary>
/// 迭代器方法使用yield关键字
/// </summary>
/// <returns></returns>
public static ienumerable<int> getnumberswithyield()
{
for (int i = 0; i < 6; i++)
{
yield return i;
}
}
/// <summary>
/// 传统迭代方法返回一个list<int>
/// </summary>
/// <returns></returns>
public static list<int> getnumberswithoutyield()
{
var numbers = new list<int>();
for (int i = 0; i < 6; i++)
{
numbers.add(i);
}
return numbers;
}
输出结果:

yield延迟加载按需获取数据
yield关键字可以通过延迟执行的方式,仅在实际需要时生成数据,从而提高了性能和效率。
/// <summary>
/// yield关键字延迟加载按需获取数据
/// </summary>
public static void lazyloadingrun()
{
console.writeline("yield延迟加载按需获取数据 开始...");
foreach (var number in getevennumbers(11))
{
console.writeline($"返回值 === {number} ===");
thread.sleep(500);
}
console.writeline("yield延迟加载按需获取数据 结束...");
}
/// <summary>
/// 使用yield返回偶数的迭代器方法
/// </summary>
/// <returns></returns>
public static ienumerable<int> getevennumbers(int number)
{
for (int i = 1; i < number; i++)
{
console.writeline($"yielding {i}");
if (i % 2 == 0)
{
yield return i; //只在需要时生成偶数
}
}
}
输出结果:

yield break显式示迭代结束
yield break:显式示迭代结束,如以下示例所示:
public static void yieldbreakrun()
{
console.writeline(string.join(" ", takewhilepositive(new int[] { 1, 3, 4, 5, -1, 3, 4 })));
//输出:1 3 4 5
console.writeline(string.join(" ", takewhilepositive(new int[] { 9, 8, 7, 6, 5, -5, 88, 100 })));
//输出:9 8 7 6 5
}
public static ienumerable<int> takewhilepositive(ienumerable<int> numbers)
{
foreach (int n in numbers)
{
if (n > 0)
{
yield return n;
}
else
{
yield break;
}
}
}
什么情况不能使用yield关键字
带有 in、ref 或 out 参数的方法。
lambda 表达式和匿名方法。
在 c# 13 之前,yield 在具有 unsafe 块的任何方法中都无效。从 c# 13 开始,可以在包含 unsafe 块的方法中使用 yield,但不能在 unsafe 块中使用。
不能在catch和finally块中使用yield return和yield break。
不能在具有catch块的try块中使用yield return和yield break。
可以在只有finally块的try块中使用yield return和yield break。
到此这篇关于c#使用yield关键字实现提升迭代性能与效率的文章就介绍到这了,更多相关c# yield关键字内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网!
发表评论