Had a discussion earlier today about ArrayList versus List<T> and whether or not there was a performance gain to using List<T> when you're dealing with value types. The jury is still out on that but i'm pretty sure a List<int> will not have to box/unbox the variables and you will have to box/unbox the variables when dealing with an ArrayList... to be continued.
However, a co-worker brought up an interesting overload on the sort() and FindAll() methods of a List<T> that i wasn't aware of! The ability to send in a Predicate<T> with the FindAll() and send in a Comparison<T> with the the Sort()!
my experiment started with this bit of code, sorting a list of people, then filtering out anyone that had a certain last name. It looked like this using anonymous delegates:
using System;
using System.Collections.Generic;
using System.Text;
namespace Sorting
{
class Program
{
static void Main(string[] args)
{
List<Person> people = new List<Person>();
people.Add(new Person("Mike", "Mayer"));
people.Add(new Person("Ben", "Johnson"));
people.Add(new Person("Mark", "Baldwin"));
people.Add(new Person("Ross", "Jackson"));
people.Add(new Person("James", "Turner"));
Console.WriteLine("===People UnSorted===");
DisplayPeople(people);
Console.WriteLine();
//compare by last name
people.Sort(
delegate(Person one, Person two)
{
return one.Lastname.CompareTo(two.Lastname);
}
);
Console.WriteLine("===People Sorted===");
DisplayPeople(people);
Console.WriteLine();
//filter by 'is peckham'
List<Person> peopleFiltered =
people.FindAll(
delegate(Person P)
{
return P.Lastname.ToLower() == "johnson";
}
);
Console.WriteLine("===People who are peckham===");
DisplayPeople(peopleFiltered);
Console.WriteLine("press any key to exit");
Console.ReadKey();
}
static void DisplayPeople(IEnumerable<Person> people)
{
foreach (Person p in people)
{
Console.WriteLine("{0}, {1}", p.Lastname, p.FirstName);
}
}
}
public class Person
{
public Person(string first, string last)
{
this.FirstName = first;
this.Lastname = last;
}
private string _lastname;
public string Lastname
{
get { return _lastname; }
set { _lastname = value; }
}
private string _firstName;
public string FirstName
{
get { return _firstName; }
set { _firstName = value; }
}
}
}

it's important to note that
delegate(Person P)
{
return P.Lastname.ToLower() == "johnson";
}
is the same as saying:
Predicate<Person> pred = new Predicate<Person>(IsJohnson);
where the IsJohnson method looks like this:
static bool IsJohnson(Person P){return P.Lastname.ToLower() == "johnson";
}