Wednesday, October 20, 2004

Iterators in C# 2.0

Iterators are some thing pretty cool, they get you to use foreach withouth explicitly implementing IEnumerator/IEnumerable.

Some facts about Iterators: (source MSDN)

An iterator is a section of code that returns an ordered sequence of values.
An iterator can be used as the body of a method, an operator, or a get accessor.
The interator code uses the yield return statement to return each element in turn.
Using iterators, it is no longer necessary to implement the interfaces System.Collections.IEnumerable and System.Collections.IEnumerator when creating a collection class that supports foreach. The compiler does this work for you.
The return type of an iterator must be System.Collections.IEnumerable, System.Collections.IEnumerator or one of the generic iterator interfaces.
Iterators can be named as well (as i have done in my example).


Yeild is a new key-word in C# 2.0 following are a few important facts about it: (source MSDN)

The yield statement can only appear inside an iterator block, which might be used as a body of a method, operator, or accessor. The body of such methods, operators, or accessors is controlled by the following restrictions:

Unsafe blocks are not allowed.
Parameters to the method, operator, or accessor cannot be ref (C# Programmer's Reference) or out (C# Programmer's Reference).
A yield statement cannot appear in an anonymous method.
A yield statement cannot appear in a finally block. When used with expression, a yield statement cannot appear in a catch block or in a tryblock that has one or more catch clauses.

Now its time to see the code:



#region Using directives

using System;
using System.Collections.Generic;
using System.Text;

#endregion

namespace HelloIterators
{
#region Stack Class
///
/// My Simple Stack Class using Generics
///

/// Type Parameter
public class Stack
{
///
/// Top of the Stack
///

private int top;

///
/// Generic Collection to hold stack contents
///

private System.Collections.Generic.Collection data;


///
/// Stack Constructor
///

///
public Stack(System.Collections.Generic.Collection t)
{
data = t;
top = 0;
}

///
/// Default Constructor
///

public Stack()
{
data = new System.Collections.Generic.Collection();
top = 0;
}

///
/// Push
///

/// Item/Content to be pushed
public void push(T item)
{
data.Insert(top, item);
top++;
}

///
/// POP
///

/// Content / Item on stack top
public T pop()
{
if (top > 0)
{
top = top - 1;
return data[top];
}
else
{
throw new IndexOutOfRangeException(" Stack is already empty");
}
}

///
/// Iterator method
///

/// IEnumerable
public IEnumerable getAllItems()
{
for(int index=top-1; index>=0;index--)
{
yield return data[index];
}
}

}
#endregion
class Program
{
static void Main(string[] args)
{
// StackClassObject--See char as type paramter(this reminds me of
// C++ :))
Stack myStack = new Stack();

myStack.push('H');
myStack.push('A');
myStack.push('M');

// USING NAMED ITERATOR.
foreach (char ch in myStack.getAllItems())
{
Console.WriteLine(ch.ToString());
}

Console.ReadLine();
}
}
}

No comments: