• IEnumerable, IEnumerator接口


    IEnumerable接口

    //     Exposes the enumerator, which supports a simple iteration over a non-generic collection.
    public interface IEnumerable {// Returns an enumerator that iterates through a collection. IEnumerator GetEnumerator(); }

    IEnumerator接口

    //     Supports a simple iteration over a nongeneric collection.
    public interface IEnumerator {// Gets the current element in the collection. object Current { get; } // Advances the enumerator to the next element of the collection. bool MoveNext(); // Sets the enumerator to its initial position, which is before the first element in the collection. void Reset(); }

     示例1:

        class MyClass : IEnumerable
        {
            private int[] sources;
    
            public MyClass()
            {
                this.sources = new int[] { 0, 1, 3, 3, 4, 5, 5, 7, 8, 1, 3, 4, 9, 9, 9, 9, 90, 0, 0 };
            }
    
            public int this[int index]
            {
                get { return this.sources[index]; }
            }
    
            public int Length { get { return this.sources.Length; } }
    
            public IEnumerator GetEnumerator()
            {
                return new MyClassEnumerator(this);
            }
        }
    
        class MyClassEnumerator : IEnumerator
        {
            private MyClass myobject;
            private int index = -1;
    
            public MyClassEnumerator(MyClass myobject)
            {
                this.myobject = myobject;
            }
    
            public object Current
            {
                get { return this.myobject[index]; }
            }
    
            public bool MoveNext()
            {
                if (this.index < this.myobject.Length - 1)
                {
                    this.index++;
                    return true;
                }
    
                return false;
            }
    
            public void Reset() { this.index = -1; }
        }
    
            static void Main(string[] args)
            {
                MyClass myobject = new MyClass();
    
                foreach (var item in myobject)
                {
                    Console.WriteLine(item);
                }
    
                return;
            }
    View Code

    示例2: 用yield关键字简化实现.

    yield是一个语法糖, 编译器会重新翻译这段代码, 实际上是返回了一个实现了IEnumerator 的对象, 每一次的yield循环对应MoveNext, return this[i]对应于Current属性.

    参考:http://www.cnblogs.com/artech/archive/2013/04/14/yield-in-wcf-02.html

        class MyClass : IEnumerable
        {
            private int[] sources;
    
            public MyClass()
            {
                this.sources = new int[] { 0, 1, 3, 3, 4, 5, 5, 7, 8, 1, 3, 4, 9, 9, 9, 9, 90, 0, 0 };
            }
    
            public int this[int index]
            {
                get { return this.sources[index]; }
            }
    
            public int Length { get { return this.sources.Length; } }
    
            public IEnumerator GetEnumerator()
            {
                //return new MyClassEnumerator(this);
                for (int i = 0; i < this.Length; i++)
                {
                    yield return this[i];
                }
            }
        }

    示例3: 一个对象同时实现了IEnumerable, IEnumerator. 这个实例仅供实验研究, 不推荐实际中应用.

    提问: 为什么还要实现IEnumerable, 直接实现了IEnumerator就可以foreach不行吗?

    回答: 请把枚举器想象成类似指针的功能, 可以遍历指向的集合.但是一个集合对象最好允许有多个枚举器, 如果集合对象直接实现IEnumerator, 集合对象和枚举器就耦合在一起,一个集合对象就只能有一个枚举器了,也就是它本身就是自己的枚举器。就算是不考虑支持多种枚举器,只考虑对一个枚举器的同时进行多次枚举,只实现IEnumerable也是做不到。

     1     class MyClass : IEnumerable, IEnumerator
     2     {
     3         private int[] sources;
     4         private int index = -1;
     5 
     6         public MyClass()
     7         {
     8             this.sources = new int[] { 0, 1, 3, 3, 4, 5, 5, 7, 8, 1, 3, 4, 9, 9, 9, 9, 90, 0, 0 };
     9         }
    10 
    11         public int this[int index]
    12         {
    13             get { return this.sources[index]; }
    14         }
    15 
    16         public int Length { get { return this.sources.Length; } }
    17 
    18         public IEnumerator GetEnumerator()
    19         {
    20             //return new MyClassEnumerator(this);
    21             for (int i = 0; i < this.Length; i++)
    22             {
    23                 yield return this[i];
    24             }
    25         }
    26 
    27         public object Current
    28         {
    29             get { return this[index]; }
    30         }
    31 
    32         public bool MoveNext()
    33         {
    34             if (this.index < this.Length - 1)
    35             {
    36                 this.index++;
    37                 return true;
    38             }
    39 
    40             return false;
    41         }
    42 
    43         public void Reset() { this.index = -1; }
    44     }
    45 
    46         static void Main(string[] args)
    47         {
    48             MyClass myobject = new MyClass();
    49 
    50             foreach (var item in myobject)
    51             {
    52                 Console.WriteLine(item);
    53             }
    54 
    55          }

    参考:

    http://www.cnblogs.com/artech/archive/2013/04/14/yield-in-wcf-02.html

  • 相关阅读:
    Creating and Using Static Libraries for iPhone using Xcode 4.3
    Build fat static library (device + simulator) using Xcode and SDK 4+
    How to safely shut down a loading UIWebView in viewWillDisappear?
    处理iOS设备的屏幕旋转
    Instruments Tutorial for iOS: How To Debug Memory Leaks【转】
    自定义UINavigationBar的背景【转】
    iOS编程——Objective-C KVO/KVC机制[转]
    ios PNG Crush error (PNG图片错误)
    实现自定义延迟加载的滚动视图
    Linux添加或修改ssh端口
  • 原文地址:https://www.cnblogs.com/dirichlet/p/3264096.html
Copyright © 2020-2023  润新知