1. foreach

C#编译器会把foreach语句转换为IEnumerable接口的方法和属性。

foreach (Person p in persons)
{
Console.WriteLine(p);
}

foreach语句会解析为下面的代码段。

调用GetEnumerator()方法,获得数组的一个枚举

在while循环中,只要MoveNext()返回true,就一直循环下去

用Current属性访问数组中的元素

IEnumerator enumerator = persons. GetEnumerator();
while (enumerator.MoveNext())
{
Person p = (Person) enumerator.Current;
Console.WriteLine(p);
}

2. yield语句

yield语句的两种形式:

yield return <expression>;
yield break;

使用一个yield return语句返回集合的一个元素

包含yield语句的方法或属性是迭代器。迭代器必须满足以下要求

a. 返回类型必须是IEnumerableIEnumerable<T>IEnumeratorIEnumerator<T>

b. 它不能有任何ref或out参数

yield return语句不能位于try-catch快。yield return语句可以位于try-finally的try块

try
{
// ERROR: Cannot yield a value in the boday of a try block with a catch clause
yield return "test";
}
catch
{ } try
{
//
yield return "test again";
}
finally
{ } try
{ }
finally
{
// ERROR: Cannot yield in the body of a finally clause
yield return "";
}

yield break语句可以位于try块或catch块,但是不能位于finally块

下面的例子是用yield return语句实现一个简单集合的代码,以及用foreach语句迭代集合

using System;
using System.Collections.Generic; namespace ConsoleApplication6
{
class Program
{
static void Main(string[] args)
{
HelloCollection helloCollection = new HelloCollection();
foreach (string s in helloCollection)
{
Console.WriteLine(s);
Console.ReadLine();
}
}
} public class HelloCollection
{ public IEnumerator<String> GetEnumerator()
{
// yield return语句返回集合的一个元素,并移动到下一个元素上;yield break可以停止迭代
yield return "Hello";
yield return "World";
}
}
}

使用yield return语句实现以不同方式迭代集合的类:

using System;
using System.Collections.Generic; namespace ConsoleApplication8
{
class Program
{
static void Main(string[] args)
{
MusicTitles titles = new MusicTitles();
foreach (string title in titles)
{
Console.WriteLine(title);
}
Console.WriteLine(); foreach (string title in titles.Reverse())
{
Console.WriteLine(title);
}
Console.WriteLine(); foreach (string title in titles.Subset(, ))
{
Console.WriteLine(title);
Console.ReadLine();
}
}
} public class MusicTitles
{
string[] names = { "a", "b", "c", "d" };
public IEnumerator<string> GetEnumerator()
{
for (int i = ; i < ; i++)
{
yield return names[i];
}
} public IEnumerable<string> Reverse()
{
for (int i = ; i >= ; i--)
{
yield return names[i];
}
} public IEnumerable<string> Subset(int index, int length)
{
for (int i = index; i < index + length; i++)
{
yield return names[i];
}
}
}
}

以上动图由“图斗罗”提供

C#中的foreach和yield的更多相关文章

  1. .net 反射访问私有变量和私有方法 如何创建C# Closure ? C# 批量生成随机密码,必须包含数字和字母,并用加密算法加密 C#中的foreach和yield 数组为什么可以使用linq查询 C#中的 具名参数 和 可选参数 显示实现接口 异步CTP(Async CTP)为什么那样工作? C#多线程基础,适合新手了解 C#加快Bitmap的访问速度 C#实现对图片文件的压

    以下为本次实践代码: using System; using System.Collections.Generic; using System.ComponentModel; using System ...

  2. C#中的IEnumerator、foreach、yield

    [C#中的IEnumerator.foreach.yield] 1.IEnumerator,是一个接口,它的方法如下: 2.foreach语句,在编译后会变成IEnumerator的调用: 3.yie ...

  3. C#编程(三十五)----------foreach和yield

    枚举 在foreach语句中使用枚举,可以迭代集合中的元素,且无需知道集合中的元素个数. 数组或集合实现带GetEumerator()方法的IEumerable接口.GetEumerator()方法返 ...

  4. “mybatis 中使用foreach 传

    为了帮助网友解决“mybatis 中使用foreach 传”相关的问题,中国学网通过互联网对“mybatis 中使用foreach 传”相关的解决方案进行了整理,用户详细问题包括:mybatismap ...

  5. 【吐血推荐】简要分析unity3d中剪不断理还乱的yield

    在学习unity3d的时候很容易看到下面这个例子: void Start () { StartCoroutine(Destroy()); } IEnumerator Destroy(){ yield ...

  6. C#中的foreach语句与枚举器接口(IEnumerator)及其泛型 相关问题

    这个问题从<C#高级编程>数组一节中的foreach语句(6.7.2)发现的. 因为示例代码与之前的章节连贯,所以我修改了一下,把自定义类型改为了int int[] bs = { 2, 3 ...

  7. Unity 3D中不得不说的yield协程与消息传递

    1. 协程 在Unity 3D中,我们刚开始写脚本的时候肯定会遇到类似下面这样的需求:每隔3秒发射一个烟花.怪物死亡后20秒再复活之类的.刚开始的时候喜欢把这些东西都塞到Update里面去,就像下面这 ...

  8. 基于mysql对mybatis中的foreach进行深入研究

    鉴于上一篇博文一次修改mysql字段类型引发的技术探究提到的,要对foreach里面的collection相关的内容做一些介绍,今天就围绕foreach,做一些数据插入和查询相关的研究. 首先介绍一下 ...

  9. 在弹框中获取foreach中遍历的id值,并传递给地址栏(方法2)

    1.php有时候我们需要再弹框中获取foreach中遍历的数据(例如id),在弹框中点击按钮并传递给地址栏跳转.那么应该怎么做呢.第二种方法. 2. 可以在弹框中给出一个input hidden 点击 ...

随机推荐

  1. Xilinx DDR3 IP核使用问题汇总(持续更新)和感悟

    一度因为DDR3的IP核使用而发狂. 后来因为解决问题,得一感悟.后面此贴会完整讲述ddr3 ip的使用.(XILINX K7) 感悟:对于有供应商支持的产品,遇到问题找官方的流程.按照官方的指导进行 ...

  2. Hybird App ( 混合模式移动应用)开发初体验

    最近1,2个月一直都尝试开发一款Hybird app,遇到了很多问题,谈谈自己的体会. Hybird app (混合模式移动应用),它利用例如安卓端webview组件+HTML5内嵌的方式混合的方式开 ...

  3. Creating Dialogbased Windows Application (2) / 创建基于对话框的Windows应用程序(二)Button的应用、新建子窗体 / VC++, Windows

    创建基于对话框的Windows应用程序(二) —— Button的应用.新建子窗体 可以发现上一节创建的窗体中,点击OK和Cancel两个按钮是没有任何反应的.现在我们来为他们添加退出对话框的功能. ...

  4. mvn test中文乱码处理

    mvn test执行测试的时候调用的实际是maven-surefire-plugin插件因为mvn启动时会新建一个jvm进程,默认没有指定编码所以中文乱码了.启动时`<argLine>-D ...

  5. python如何连接mysql数据库

    先花点时间来说说一个程序怎么和数据库进行交互1.和数据库建立连接2.执行sql语句,接收返回值3.关闭数据库连接使用MySQLdb也要遵循上面的几步.让我们一步步的进行. 1.MySQL数据库要用My ...

  6. Oracle基础学习登陆SQLPLUS(一)

    SQLPLUS是ORACLE公司开发的非常简洁的管理工具,SQLPLUS是最好的,最核心的ORACLE管理工具.SQLPLUS简洁而高效,舍弃浮华,反璞归真.使用sqlplus,进入sqlplus并进 ...

  7. python 开发技巧(4)-- 用PyCharm实用技巧(我自己常用的)

    pycharm快捷键 1.快速导入类 Ctrl + Alt + Space 2.追踪类和方法的定义 Ctrl + b 3.复制当前行 Ctrl + d 4.移动当前行 Ctrl + Shift + ( ...

  8. .net 连接Redis

    Redis安装 公司业务需要,弄了个类似于消息队列的东西,由客户端一直轮询取得信息.之前一直是走表的,但是效率以对表的使用都太过频繁,想试着用一下Redis,看看效率怎么样. 首先是安装Redis,这 ...

  9. ios -bitmap上下文生成图片 生成水印

    - (void)test { // 0. 加载背景图片 UIImage *image = [UIImage imageNamed:@"psb"]; // 1.创建bitmap上下文 ...

  10. nyoj677 谍战

    本题能够说是最小割入门级题目. 假设能想到是最小割问题.那么建图思路便是水到渠成的事了. 加入一个源点S和汇点T: 把S与每一个间谍相连.容量为无穷大: 把城市N(即飞机场的位置)与汇点T相连.容量为 ...