The C# Programming Language
by Scott Wiltamuth


Example 1:
class Stack
{
  private int size = 0; 
  private object[] values = new object[10];
}



Example 2:
class Test
{
	static void Main() {
		int i = 123;
		object o = i;		// boxing
		int j = (int) o;	// unboxing
	}
}

Example 3:
Console.WriteLine("Stack s = {0}", s);
while (s.Count > 0) 
	Console.WriteLine("Popped {0}", s.Pop());
		Console.WriteLine("Stack s = {0}", s);

Example 4:

using System;
class Stack
{
	...
	public const int DefaultCapacity = 10;
	...
}
class Test
{
	static void Main() {
		Console.WriteLine("DefaultCapacity = {0}", Stack.DefaultCapacity);
	}
}

Example 5:

(a)
class Stack
{
	private int size = 0; 
	private object[] values = new object[10];
	...
}

(b)

class Stack
{
	private int size = 0; 
	private object[] values = new object[10];
	public Stack(): base() {
	}
	...

Example 6
public virtual void Push(object o) {
	if (size == values.Length)
		Capacity = size * 2;
	values[size++] = o;
}


Example 7:
(a)
Stack s = ...;
foreach(int i in s)
	Console.WriteLine(i);
(b)

Stack s = ...;
IEnumerable enumerable = (IEnumerable) s;
IEnumerator enumerator = enumerable.GetEnumerator();
while (enumerator.MoveNext()) {
	int i = (int) enumerator.Current;
	Console.WriteLine(i);
}



Listing One
using System;
class Stack
{
	private int size = 0; 
	private object[] values = new object[10];
	public virtual int Count { 
		get { return size; }	
	}
	public virtual object Pop() {
		if (size == 0) 
			throw new InvalidOperationException();
		else {
			object ans = values[--size];
			values[size] = null; 
			return ans;
		}
	}
	public virtual void Push(object o) {
		if (size == values.Length)
			throw new InvalidOperationException();
		values[size++] = o;		
	}
	public override string ToString() { 
		return ToString(",");
	}
	public virtual string ToString(string delimiter) { 
		switch (size) {
			case 0:
				return "";
			case 1:
				return values[0].ToString();
			default:
				string ans = "";
				for (int i = size-1; i > 0; i--)
					ans += values[i].ToString() + delimiter;
				ans += values[0];
				return ans;
		}
	}
}


Listing Two
using System;
class Test
{
	static void Main() {
		Stack s = new Stack();
		for (int i = 1; i <= 5; i++) {
			s.Push(i); 
		}
		Console.WriteLine("Stack s = {0}", s);
		while (s.Count > 0) 
			Console.WriteLine("Popped {0}", s.Pop());
		Console.WriteLine("Stack s = {0}", s);
	}
}


Listing Four
using System;
class Stack
{
	private int size = 0; 
	private object[] values = new object[10];
	public virtual int Count { 
		get { return size; }	
	}
	public virtual object Pop() {
		if (size == 0) 
			throw new InvalidOperationException();
		else {
			object ans = values[--size];
			values[size] = null; 
			return ans;
		}
	}
	public virtual void Push(object o) {
		if (size == values.Length)
			throw new InvalidOperationException();
		values[size++] = o;		
	}
	public override string ToString() { 
		return ToString(",");
	}
	public virtual string ToString(string delimiter) { 
		switch (size) {
			case 0:
				return "";
			case 1:
				return values[0].ToString();
			default:
				string ans = "";
				for (int i = size-1; i > 0; i--)
					ans += values[i].ToString() + delimiter;
				ans += values[0];
				return ans;
		}
	}
}
class Test
{
	static void Main() {
		Stack s = new Stack();
		for (int i = 1; i <= 5; i++) {
			s.Push(i); 
		}
		Console.WriteLine("Stack s = {0}", s);
		while (s.Count > 0) 
			Console.WriteLine("Popped {0}", s.Pop());
		Console.WriteLine("Stack s = {0}", s);
	}
}

using System;
class Test
{
	static void Main() {
		Stack a = new Stack();
		Console.WriteLine(a.Capacity);
		Stack b = new Stack(2);
		Console.WriteLine(b.Capacity);
		Stack c = new Stack(100);
		Console.WriteLine(c.Capacity);
		for (int i = 1; i <= 15; i++)
			a.Push(i);
		Console.WriteLine("Count={0}, Capacity={1}, Elements={2}", 
					a.Count, 
					a.Capacity, 
					a.ToString());
	}
}


Listing Six
using System;
class Stack
{
	private int size;
	private object[] values;
	public Stack(): this(DefaultCapacity) {}
	public Stack(int capacity) { 
		if (capacity <= 0)
			throw new ArgumentOutOfRangeException();
		values = new object[capacity];
		size = 0;
	}
	public const int DefaultCapacity = 10;
	...
}
class Test
{
	static void Main() {
		Stack a = new Stack();
		Stack b = new Stack(10);
		Stack c = new Stack(100);
	}
}


Listing Seven
class Stack
{
	...
	public virtual int Capacity {
		get { 
			return values.Length; 
		}
		set {
			if ((value <= size) || (value <= 0))
				throw new ArgumentOutOfRangeException();
			object[] newValues = new object[value];
			Array.Copy(values, 0, newValues, 0, size);
			values = newValues;
		}
	}
	...
}


Listing Eight

using System;
class Stack 
{
	private int size;
	private object[] values;
	public Stack(): this(DefaultCapacity) {}
	public Stack(int capacity) {
		if (capacity <= 0)
			throw new ArgumentOutOfRangeException();
		values = new object[capacity];
		size = 0;
	}
	public virtual int Capacity {
		get { 
			return values.Length; 
		}
		set {
			if ((value <= size) || (value <= 0))
				throw new ArgumentOutOfRangeException();
			object[] newValues = new object[value];
			Array.Copy(values, 0, newValues, 0, size);
			values = newValues;
		}
	}
	public virtual int Count {
		get { return size; }
	}
	public const int DefaultCapacity = 10;
	public virtual object Pop() {
		if (size == 0) 
			throw new InvalidOperationException();
		else {
			object ans = values[--size];
			values[size] = null;
			return ans;
		}
	}
	public virtual void Push(object o) {
		if (size == values.Length)
			Capacity = size * 2;
		values[size++] = o;
	}
	public override string ToString() {
		return ToString(",");
	}
	public virtual string ToString(string delimiter) {
		switch (size) {
			case 0:
				return "";
			case 1:
				return values[0].ToString();
			default:
				string ans = "";
				for (int i = size-1; i > 0; i--)
					ans += values[i].ToString() + delimiter;
				ans += values[0];
				return ans;
		}
	}
}
class Test
{
	static void Main() {
		Stack a = new Stack();
		Console.WriteLine(a.Capacity);
		Stack b = new Stack(2);
		Console.WriteLine(b.Capacity);
		Stack c = new Stack(100);
		Console.WriteLine(c.Capacity);
		for (int i = 1; i <= 15; i++)
			a.Push(i);
		Console.WriteLine("Count={0}, Capacity={1}, Elements={2}", 
					a.Count, 
					a.Capacity, 
					a.ToString());
	}
}


Listing Nine
class Test
{
	static void Main() {
		Stack s = new Stack();
		for (int i = 1; i < 10; i++)
			s.Push(i);
		foreach (int i in s)
			Console.WriteLine(i);
	}
}


Listing Ten

using System;
delegate void EmptyDelegate();
class Test
{
	static void F() {
		Console.WriteLine("F");
	}
	static void Main() {
		EmptyDelegate d = new EmptyDelegate(F);
		d();
	}
}


Listing Eleven
using System;
class Stack
{
	...
	public event EventHandler Changed;
	protected virtual void OnChanged(EventArgs e) {
		if (Changed != null)
			Changed(this, e);
	}
	...
}


Listing Twelve

public virtual object Pop() {
	if (size == 0) 
		throw new InvalidOperationException();
	else {
		object ans = values[--size];
		values[size] = null;
		OnChanged(EventArgs.Empty);
		return ans;
	}
}
public virtual void Push(object o) {
	if (size == values.Length)
		Capacity = size * 2;
	values[size++] = o;		
	OnChanged(EventArgs.Empty);
}

Listing Thirteen
using System;
class Test 
{
	static void Stack_Changed(object sender, EventArgs e) {
		Console.WriteLine("The stack changed: {0}", sender);
	}
	static void Main() {
		Stack s = new Stack();
		s.Changed += new EventHandler(Stack_Changed);
		for (int i = 1; i <= 10; i++)
			s.Push(i);
		while (s.Count >= 0)
			s.Pop();
	}
}


Listing Fourteen
namespace System.Collections
{
	public interface IEnumerable
	{
		IEnumerator GetEnumerator();
	}
	public interface IEnumerator
	{
		object Current { get; }
		bool MoveNext();
		void Reset();
	}
}


Listing Fifteen
using System;
using System.Collections;
class Stack: IEnumerable 
{
	public virtual IEnumerator GetEnumerator() { 
		return new Enumerator(this);
	}
	private class Enumerator: IEnumerator 
	{
		public Enumerator(Stack stack) {...}
		public virtual object Current { get {...} }
		public virtual bool MoveNext() {...}
		public virtual void Reset() {...}
	}
	...
}

Listing Sixteen
using System;
using System.Collections;
class Stack: IEnumerable
{
	private int size;
	private object[] values;
	public Stack(): this(DefaultCapacity) {}
	public Stack(int capacity) {
		if (capacity <= 0)
			throw new ArgumentOutOfRangeException();
		values = new object[capacity];
		size = 0;
	}
	public virtual int Capacity {
		get { 
			return values.Length; 
		}
		set {
			if ((value <= size) || (value <= 0))
				throw new ArgumentOutOfRangeException();
			object[] newValues = new object[value];
			Array.Copy(values, 0, newValues, 0, size);
			values = newValues;
		}
	}
	public event EventHandler Changed;
	public virtual int Count {
		get { return size; }
	}
	public const int DefaultCapacity = 10;
	private class Enumerator: IEnumerator
	{
		private int currIndex;
		private bool dirty;
		private Stack stack;
		private void Stack_Changed(object sender, EventArgs e) {
			dirty = true;
			stack = null;
		}
		public Enumerator(Stack stack) {
			this.stack = stack;
			stack.Changed += new EventHandler(Stack_Changed);
			dirty = false;
			Reset();
		}
		public virtual object Current {
			get {
				ThrowIfDirty();
				if ((currIndex == stack.size) || (currIndex == -1))
					throw new InvalidOperationException();
				return stack.values[currIndex];
			}
		}
		public virtual bool MoveNext() {
			ThrowIfDirty();
			if (currIndex == -1)
				return false;
			return --currIndex >= 0;
		}
		public virtual void Reset() {
			ThrowIfDirty();
			currIndex = stack.size;
		}
		private void ThrowIfDirty() {
			if (dirty)
				throw new InvalidOperationException();
		}
	}
	public virtual IEnumerator GetEnumerator() {
		return new Enumerator(this);
	}
	protected virtual void OnChanged(EventArgs e) {
		if (Changed != null)
			Changed(this, e);
	}
	public virtual object Pop() {
		if (size == 0) 
			throw new InvalidOperationException();
		else {
			object ans = values[--size];
			values[size] = null;
			OnChanged(EventArgs.Empty);
			return ans;
		}
	}
	public virtual void Push(object o) {
		if (size == values.Length)
			Capacity = size * 2;
		values[size++] = o;		
		OnChanged(EventArgs.Empty);
	}
	public override string ToString() {
		return ToString(",");
	}
	public virtual string ToString(string delimiter) {
		switch (size) {
			case 0:
				return "";
			case 1:
				return values[0].ToString();
			default:
				string ans = "";
				for (int i = size-1; i > 0; i--)
					ans += values[i].ToString() + delimiter;
				ans += values[0];
				return ans;
		}
	}
}
class Test
{
	static void Main() {
		Stack s = new Stack();
		for (int i = 1; i < 10; i++)
			s.Push(i);
		foreach (int i in s)
			Console.WriteLine(i);
	}
}




