using System; using System.Collections; class Album : IComparable, ICloneable { private string _Title; private string _Artist; public Album(string artist, string title) { _Artist = artist; _Title = title; } public string Title { get { return _Title; } set { _Title = value; } } public string Artist { get { return _Artist; } set { _Artist = value; } } public override string ToString() { return _Artist + ", " + _Title; } public int CompareTo(object o) { Album other = o as Album; if (other == null) throw new ArgumentException(); if (_Artist != other._Artist) return _Artist.CompareTo(other._Artist); else return _Title.CompareTo(other._Title); } public object Clone() { return new Album(_Artist, _Title); } } class TitleComparer : IComparer { public int Compare(object l, object r) { Album left = l as Album; Album right = r as Album; if ((left == null) || (right == null)) throw new ArgumentException(); if (left.Title != right.Title) return left.Title.CompareTo(right.Title); else return left.Artist.CompareTo(right.Artist); } } class Class1 { static void Main(string[] args) { ArrayList arr = new ArrayList(); arr.Add(new Album("G", "A")); arr.Add(new Album("B", "G")); arr.Add(new Album("S", "A")); arr.Sort(); try { foreach (Album a in arr) { Console.WriteLine(a); } } catch (System.InvalidCastException e) { } arr.Sort(new TitleComparer()); foreach (Album a in arr) { Console.WriteLine(a); } Album l = new Album("L", "G"); arr.Sort(); int index = arr.BinarySearch(l); Console.WriteLine(index.ToString()); arr.Sort(new TitleComparer()); index = arr.BinarySearch(l, new TitleComparer()); Console.WriteLine(index.ToString()); } }
Class Interface
Implement ICloneable, IComparable
using System; using System.Runtime.Serialization; using System.Collections; public class ComplexOverflowException : ApplicationException { public ComplexOverflowException() : base() { } public ComplexOverflowException(string msg) : base(msg) { } public ComplexOverflowException(SerializationInfo info, StreamingContext cxt) : base(info, cxt) { } public ComplexOverflowException(string msg, Exception inner) : base(msg, inner) { } } public class Complex : ICloneable, IComparable { private double realPart = 0.0; private double imagPart = 0.0; public Complex() { } public Complex(double r) : this(r, 0) { } public Complex(double r, double i) { realPart = r; imagPart = i; } public Complex(Complex l) { realPart = l.realPart; imagPart = l.imagPart; } public double Imaginary { get { return imagPart; } set { imagPart = value; } } public double Real { get { return realPart; } set { realPart = value; } } public void Scale(double val) { double tempImaginary = val * imagPart; realPart *= val; imagPart = tempImaginary; } static public Complex operator +(Complex l, Complex r) { Complex result = new Complex(l); result.realPart += r.realPart; result.imagPart += r.imagPart; return result; } static public Complex operator *(Complex l, Complex r) { Complex result = new Complex(); checked { result.Real = l.Real * r.Real - l.Imaginary * r.Imaginary; result.Imaginary = l.Real * r.Imaginary + l.Imaginary * r.Real; } return result; } static public bool operator ==(Complex l, Complex r) { return ((l.Real == r.Real) && (l.Imaginary == r.Imaginary)); } static public bool operator !=(Complex l, Complex r) { return !(l == r); } static public bool operator >(Complex l, Complex r) { double normL = l.imagPart * l.imagPart + l.realPart * l.realPart; double normR = r.imagPart * r.imagPart + r.realPart * r.realPart; return normL > normR; } static public bool operator <(Complex l, Complex r) { return r > l; } public override bool Equals(object o) { if (!(o is Complex)) return false; Complex c = (Complex)o; return ((c.Real == Real) && (c.Imaginary == Imaginary)); } public override int GetHashCode() { return (int)(Real + Imaginary); } object ICloneable.Clone() { return new Complex(this); } int IComparable.CompareTo(object o) { if (!(o is Complex)) throw new ArgumentException("Object is not a complex number"); Complex c = (Complex)o; double norm = imagPart * imagPart + realPart * realPart; double normO = c.imagPart * c.imagPart + c.realPart * c.realPart; if (norm > normO) return 1; else if (normO > norm) return -1; else return 0; } } class MainClass { public static IComparable theMax(IComparable seed, IEnumerable coll) { foreach (IComparable c in coll) { if (c.CompareTo(seed) > 0) { seed = c; } } return seed; } static void Main(string[] args) { Complex[] cArray = new Complex[100]; Complex max = new Complex(0, 0); max = (Complex)theMax(max, cArray); } }
Implements IComparable
using System;
using System.Collections;
using System.Collections.Generic;
using System.Text;
class Person : IComparable {
public string Name;
public int Age;
public Person(string name, int age) {
Name = name;
Age = age;
}
public int CompareTo(object obj) {
if (obj is Person) {
Person otherPerson = obj as Person;
return this.Age – otherPerson.Age;
} else {
throw new ArgumentException(
“Object to compare to is not a Person object.”);
}
}
}
class Program {
static void Main(string[] args) {
ArrayList list = new ArrayList();
list.Add(new Person(“A”, 30));
list.Add(new Person(“B”, 25));
list.Add(new Person(“B”, 27));
list.Add(new Person(“E”, 22));
for (int i = 0; i < list.Count; i++) { Console.WriteLine("{0} ({1})", (list[i] as Person).Name, (list[i] as Person).Age); } list.Sort(); for (int i = 0; i < list.Count; i++) { Console.WriteLine("{0} ({1})", (list[i] as Person).Name, (list[i] as Person).Age); } } } [/csharp]
Demonstrate a destructor
/*
C#: The Complete Reference
by Herbert Schildt
Publisher: Osborne/McGraw-Hill (March 8, 2002)
ISBN: 0072134852
*/
// Demonstrate a destructor.
using System;
class Destruct {
public int x;
public Destruct(int i) {
x = i;
}
// called when object is recycled
~Destruct() {
Console.WriteLine(“Destructing ” + x);
}
// generates an object that is immediately destroyed
public void generator(int i) {
Destruct o = new Destruct(i);
}
}
public class DestructDemo1 {
public static void Main() {
int count;
Destruct ob = new Destruct(0);
/* Now, generate a large number of objects. At
some point, garbage collection will occur.
Note: you might need to increase the number
of objects generated in order to force
garbage collection. */
for(count=1; count < 100000; count++) ob.generator(count); Console.WriteLine("Done"); } } [/csharp]
Illustrates a destructor
/* Mastering Visual C# .NET by Jason Price, Mike Gunderloy Publisher: Sybex; ISBN: 0782129110 */ /* Example5_14.cs illustrates a destructor */ // declare the Car class class Car { // define the destructor ~Car() { System.Console.WriteLine("In ~Car() destructor"); // do any cleaning up here } } public class Example5_14 { public static void Main() { // create a Car object Car myCar = new Car(); System.Console.WriteLine("At the end of Main()"); } }
Shows that stack unwinding in C# does not necessarily call destructors
/* C# Programming Tips & Techniques by Charles Wright, Kris Jamsa Publisher: Osborne/McGraw-Hill (December 28, 2001) ISBN: 0072193794 */ // Unwind.cs -- Shows that stack unwinding in C# does not necessarily call // destructors. // Compile this program with the following command line: // C:>csc Unwind.cs // namespace nsStack { using System; using System.IO; public class Unwind { static public void Main () { Unwind main = new Unwind(); // Set up the try ... catch block try { main.TestStack (); } catch (FileNotFoundException e) { // Show the contents of the Message string in each class object if (clsFirst.Message == null) Console.WriteLine ("First message is null"); else Console.WriteLine (clsFirst.Message); if (clsFirst.Message == null) Console.WriteLine ("Second message is null"); else Console.WriteLine (clsSecond.Message); if (clsFirst.Message == null) Console.WriteLine ("Third message is null"); else Console.WriteLine (clsThird.Message); // Show the exception object message Console.WriteLine (e.Message); } } void TestStack () { // Create a new clsFirst object and call a method in it clsFirst first = new clsFirst (); first.FirstFunc(); } } class clsFirst { ~clsFirst () { Message = "clsFirst destructor called"; } static public string Message = null; public void FirstFunc() { // Create a new clsSecond object and call a method in it clsSecond second = new clsSecond(); second.SecondFunc (); } } class clsSecond { ~clsSecond () { Message = "clsSecond destructor called"; } static public string Message = null; public void SecondFunc() { // Create a new clsThird object and call a method in it clsThird third = new clsThird(); third.ThirdFunc (); } } class clsThird { ~clsThird () { Message = "clsThird destructor called"; } static public string Message = null; public void ThirdFunc() { ThrowException (); } // By the time the program gets here, it is five method calls deep. // Throw an exception to force a stack unwind. private void ThrowException () { throw (new FileNotFoundException ()); } } }
the destructors are called bottom-up, which confirms the sequencing of destructors.
using System; public class Starter { public static void Main() { XClass obj = new XClass(); } } public class MyClass { ~MyClass() { Console.WriteLine("MyClass destructor"); } } public class YClass : MyClass { ~YClass() { Console.WriteLine("YClass destructor"); } } public class XClass : YClass { ~XClass() { Console.WriteLine("XClass destructor"); } }