I need to sort a list by any one of its properties, but i dont know which of these properties it will specifically be sorted on. The Main method below.
static void Main(string[] args)
{
Things<Something> something = new Things<Something>();
something.Add(new Something
{ Thing = "Apartment", Price = 1500000 });
something.Add(new Something
{ Thing = "Bed", Price = 10000 });
something.Add(new Something
{ Thing = "Lamp", Price = 600 });
something.Add(new Something
{ Thing = "Car", Price = 5000000 });
Console.WriteLine("\n\tStuff sorted by description");
something = something.SelectionSort("Thing");
foreach (Something thing in something)
Console.WriteLine("\t" + thing);
Console.WriteLine("\n\tStock items sorted by value");
something = something.SelectionSort("Value");
foreach (Something thing in something)
Console.WriteLine("\t" + thing);
Console.Write("\n\tPress any key to exit ...");
Console.ReadKey();
}
I have a struct
public struct Something
{
public string Thing { get; set; }
public decimal Price { get; set; }
}
And a generic container class called things
public class Things<T> : IEnumerable<T>
{
private List<T> lstItems;
public int Count { get { return lstItems.Count; } }
public Things() { lstItems = new List<T>(); }
public Things(List<T> items_) { lstItems = new List<T>(items_); }
public void Add(T item)
{
lstItems.Add(item);
}
public T this[int i]
{
get { return lstItems[i]; }
set { lstItems[i] = value; }
}
IEnumerator IEnumerable.GetEnumerator()
{
throw new System.NotImplementedException();
}
public IEnumerator<T> GetEnumerator()
{
foreach (T item in lstItems)
yield return item;
}
}
An extensions class extends the generic container class
public static class ExtensionsClass
{
private static string SortFiield { get; set; }
private static object GetProperty<T>(T thing, string nameofProp)
{
return thing.GetType().GetProperty(nameofProp).GetValue(thing, null);
}
private static int Compare<T>(T x, T y)
{
IComparable propX = (IComparable)GetProperty(x, SortFiield);
IComparable propY = (IComparable)GetProperty(y, SortFiield);
return propX.CompareTo(propY);
}
public static Things<T> SelectionSort<T>(this Things<T> things, string SORTFIELD)
{
List<T> lsstt = new List<T>(things);
int iIndex;
T temporary;
SortFiield = SORTFIELD;
for (int i = 0; i < lsstt.Count - 1; i++)
{
iIndex = i;
for (int j = i + 1; j < lsstt.Count; j++)
{
string first = GetProperty(lsstt[j], SortFiield).ToString();
string second = GetProperty(lsstt[iIndex], SortFiield).ToString();
if (Compare(first, second) < 0)
iIndex = j;
}
temporary = lsstt[i];
lsstt[i] = lsstt[iIndex];
lsstt[iIndex] = temporary;
}
return new Things<T>(lsstt);
}
}
The problem i am encountering is that get property in the extension class returns null, but i know that the object i am trying to return exists. It is found by the "String first = ...." line but when getproperty is called from the Compare method then it returns null.
You are passing "first", "second" to Compare. In your case both of them are strings and not objects, you need to pass "lsstt[j]" and "lsstt[iIndex]" to it.
if (Compare(lsstt[j], lsstt[iIndex]) < 0)
iIndex = j;