服务器之家:专注于VPS、云服务器配置技术及软件下载分享
分类导航

PHP教程|ASP.NET教程|Java教程|ASP教程|编程技术|正则表达式|C/C++|IOS|C#|Swift|Android|VB|R语言|JavaScript|易语言|vb.net|

服务器之家 - 编程语言 - C# - 解析c# yield关键字

解析c# yield关键字

2022-09-29 16:26八英里 C#

这篇文章主要介绍了c# yield关键字的相关资料,文中讲解非常细致,代码帮助大家更好的理解和学习,感兴趣的朋友可以了解下

1.yield实现的功能

yield return:

先看下面的代码,通过yield return实现了类似用foreach遍历数组的功能,说明yield return也是用来实现迭代器的功能的。

using static System.Console;
using System.Collections.Generic;

class Program
{
//一个返回类型为IEnumerable<int>,其中包含三个yield return
public static IEnumerable<int> enumerableFuc()
{
  yield return 1;
  yield return 2;
  yield return 3;
}

static void Main(string[] args)
{
  //通过foreach循环迭代此函数
  foreach(int item in enumerableFuc())
  {
    WriteLine(item);
  }
  ReadKey();
}
}

输出结果:

1
2
3

yield break:

再看下面的代码,只输出了1,2,没有输出3,说明这个迭代器被yield break停掉了,所以yield break是用来终止迭代的。

using static System.Console;
using System.Collections.Generic;
class Program
{
//一个返回类型为IEnumerable<int>,其中包含三个yield return
public static IEnumerable<int> enumerableFuc()
{
  yield return 1;
  yield return 2;
  yield break;
  yield return 3;
}

static void Main(string[] args)
{
  //通过foreach循环迭代此函数
  foreach(int item in enumerableFuc())
  {
    WriteLine(item);
  }
  ReadKey();
}
}

输出结果:

1
2

2.只能使用在返回类型必须为 IEnumerable、IEnumerable<T>、IEnumerator 或 IEnumerator<T>的方法、运算符、get访问器中。

3.yield关键字的实现原理

我们用while循环代替foreach循环,发现我们虽然没有实现GetEnumerator(),也没有实现对应的IEnumerator的MoveNext(),和Current属性,但是我们仍然能正常使用这些函数。

class Program
{
//一个返回类型为IEnumerable<int>,其中包含三个yield return
public static IEnumerable<int> enumerableFuc()
{
  yield return 1;
  yield return 2;
  yield return 3;
}

static void Main(string[] args)
{
  //用while循环代替foreach
  IEnumerator<int> enumerator = enumerableFuc().GetEnumerator();
  while (enumerator.MoveNext())
  {
    int current = enumerator.Current;
    WriteLine(current);
  }
  ReadKey();
}
}

输出结果:

1
2
3

至于为什么会出现这种情况,我们可以用ILSpy对生成的exe进行反编译来找到原因。
由于直接反编译成C#会变为原样

解析c# yield关键字

所以我们选择反编译为带C#注释的IL代码,虽然可读性差点,但是可以详细的了解其中过的原理。
先来看Program翻译的情况,编译的时候自动生成了一个新的类。

解析c# yield关键字

接下来我们来仔细看这些代码,EnumerableFuc()返回了这个新的类。

解析c# yield关键字

看这个代码自动生成的类的实现,发现它继承了IEnumerable、IEnumerable<T>、IEnumerator 或 IEnumerator<T>,这时我们应该已经能猜到这个新的类就是我们没有实现对应的IEnumerator的MoveNext(),和Current属性,但是我们仍然能正常使用这些函数的原因了。

解析c# yield关键字

我们再来看一下这个类具体是如何实现迭代的呢,我们主要来看一下MoveNext()函数

解析c# yield关键字

解析c# yield关键字

每次调用MoveNext()函数都会将state加1,一共进行了4次迭代,前三次返回true,最后一次返回false,代表迭代结束。这四次迭代对应被3个yield return语句分成4部分的enumberableFuc()中的语句。

用enumberableFuc()来进行迭代的真实流程就是:

1.运行enumberableFuc()函数,获取代码自动生成的类的实例。
2.接着调用GetEnumberator()函数,将获取的类自己作为迭代器开始迭代。
3.每次运行MoveNext(),state增加1,通过switch语句可以让每次调用MoveNext()的时候执行不同部分的代码。
4。MoveNext()返回false,结束。

这也能说明yield关键字其实是一种语法糖,最终还是通过实现IEnumberable<T>、IEnumberable、IEnumberator<T>和IEnumberator接口实现的迭代功能。

以上就是解析c# yield关键字的详细内容,更多关于c# yield关键字的资料请关注服务器之家其它相关文章!

原文链接:https://www.cnblogs.com/deepalley/p/13401157.html

延伸 · 阅读

精彩推荐
  • C#C#如何更改Word的语言设置

    C#如何更改Word的语言设置

    这篇文章主要为大家详细介绍了C#如何更改Word的语言设置,具有一定的参考价值,感兴趣的小伙伴们可以参考一下...

    E-iceblue8182022-02-24
  • C#NancyFx框架检测任务管理器详解

    NancyFx框架检测任务管理器详解

    这篇文章主要为大家详细介绍了NancyFx框架检测任务管理器的相关资料,具有一定的参考价值,感兴趣的小伙伴们可以参考一下...

    Lexan5062022-01-25
  • C#C# Winfom 中ListBox的简单用法详解

    C# Winfom 中ListBox的简单用法详解

    这篇文章主要介绍了C# Winfom 中ListBox的简单用法详解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们...

    小小邪9382022-08-11
  • C#C#程序执行时间长查询速度慢解决方案

    C#程序执行时间长查询速度慢解决方案

    这篇文章主要介绍了C#程序执行时间长查询速度慢解决方案,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友...

    叶丶梓轩3702022-09-24
  • C#日常收集C#接口知识(知识全面)

    日常收集C#接口知识(知识全面)

    本文分为七章节给大家介绍c#接口知识,内容比较详细,特此分享脚本之家平台,供大家参考...

    C#教程网11942021-11-08
  • C#C# winform程序实现开机自启动并且识别是开机启动还是双击启动

    C# winform程序实现开机自启动并且识别是开机启动还是双击启动

    这篇文章主要介绍了C# winform程序实现开机自启动并且识别是开机启动还是双击启动的实现代码,代码简单易懂,非常不错,具有一定的参考借鉴价值,需要...

    碧水青荷6192022-03-03
  • C#C#生成带logo的二维码

    C#生成带logo的二维码

    带logo的二维码生成分为两步骤:首先根据输入的内容生成二维码图片,然后读取本地的logo图片,通过图片处理生成带logo的二维码。本文对此进行介绍,具...

    诸葛风流12262021-12-22
  • C#C#(.net)中按字节数截取字符串最后出现乱码问题的解决

    C#(.net)中按字节数截取字符串最后出现乱码问题的解决

    这篇文章主要给大家介绍了关于C#(.net)中按字节数截取字符串最后出现乱码问题的解决方法,文中通过示例代码介绍的非常详细,对大家的学习或者工作...

    熊仔其人11242022-02-24