C#学习笔记:foreach原理
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C#学习笔记:foreach原理相关的知识,希望对你有一定的参考价值。
这篇随笔是对上一篇随笔C#关键字:yield的扩展。
关于foreach
首先,对于 foreach ,大家应该都非常熟悉,这里就简单的描述下。
foreach 语句用于对实现 System.Collections.IEnumerable 或 System.Collections.Generic.IEnumerable<T> 接口的数组或对象集合中的每个元素进行循环访问,但不能用于在源集合中添加或移除项,否则可能产生不可预知的副作用。如果需要在源集合中添加或移除项,应使用 for 循环。
foreach的原理
foreach语句是被设计用来和可枚举类型一起使用,只要它的遍历对象是可枚举类型(实现了IEnumerable),比如数组。调用过程如下:
- 调用GetEnumerator()方法,返回一个IEnumerator引用。
- 调用返回的IEnumerator接口的MoveNext()方法。
- 如果MoveNext()方法返回true,就使用IEnumerator接口的Current属性获取对象的一个引用,用于foreach循环。
- 重复前面两步,直到MoveNext()方法返回false为止,此时循环停止。
我们可以通过代码模拟foreach的执行过程,如下:
static void Main() { int[] arr = { 1, 2, 3, 4, 5 }; // 声明并初始化数组。 IEnumerator ie = arr.GetEnumerator(); // 调用可枚举类型的GetEnumerator方法获得枚举数对象。 while (ie.MoveNext()) // 调用IEnumerator接口的MoveNext方法移到下一项。实现遍历数组。 { int i = (int)ie.Current; // 调用IEnumerator接口的Current方法获取当前项。注意它返回的是object类型,需要强制转换类型。 Console.Write("{0} ", i); } // Output: 1 2 3 4 5 Console.ReadKey(); }
当然,如果使用foreach的话,就非常简单了,如下:
static void Main() { int[] arr = { 1, 2, 3, 4, 5 }; foreach (int item in arr) { Console.Write("{0} ", item); } // Output: 1 2 3 4 5 Console.ReadKey(); }
接下来,再看一个复杂点的实例,如下:
class Program { static void Main() { // Create a Tokens instance. Tokens f = new Tokens("This is a sample sentence.", new char[] { ‘ ‘, ‘-‘ }); // Display the tokens. foreach (string item in f) { System.Console.WriteLine(item); } // Output: // This // is // a // sample // sentence. Console.ReadKey(); } } public class Tokens : IEnumerable { private string[] elements; public Tokens(string source, char[] delimiters) { // The constructor parses the string argument into tokens. elements = source.Split(delimiters); } // The IEnumerable interface requires implementation of method GetEnumerator. public IEnumerator GetEnumerator() { return new TokenEnumerator(this); } // Declare an inner class that implements the IEnumerator interface. private class TokenEnumerator : IEnumerator { private int position = -1; private Tokens t; public TokenEnumerator(Tokens t) { this.t = t; } // The IEnumerator interface requires a MoveNext method. public bool MoveNext() { if (position < t.elements.Length - 1) { position++; return true; } else { return false; } } // The IEnumerator interface requires a Reset method. public void Reset() { position = -1; } // The IEnumerator interface requires a Current method. public object Current { get { return t.elements[position]; } } } }
参考文档
- C#中foreach的原来
- http://www.cnblogs.com/mcgrady/archive/2011/11/12/2246867.html
- https://msdn.microsoft.com/zh-cn/library/9yb8xew9%28v=vs.110%29.aspx
以上是关于C#学习笔记:foreach原理的主要内容,如果未能解决你的问题,请参考以下文章