It uses the Quicksort algorithm, which is not stable when implemented efficiently (in place). Meaning that it doesn't guarantee that values which are equal retain their prior relative position after sorting.
For example, if you have a bunch of points:
Point[] points = new Point[]
{
new Point(0, 1),
new Point(0, 2),
new Point(0, 3),
new Point(1, 1),
new Point(1, 2),
new Point(1, 3)
};
And you sort these points by x-coordinate only, using this comparer:
private int CompareByX(Point a, Point b)
{
return a.X - b.X;
}
It will only guarantee that the points are sorted by their x-coordinate, meaning you could easily end up with a mixed up order (when looking at the y-coordinate):
Point(0, 3)
Point(0, 2)
Point(0, 1)
Point(1, 3)
Point(1, 2)
Point(1, 1)
[Edit]
This doesn't mean that the sorting algorithm is non-deterministic (random). For same input data, you will get same output data on each run. You can also predict the actual way it will be reorganized if you examine the algorithm precisely, but it is unnecessary. It is sufficient just to know that this happens when using the sort routine.
Here is a working example for your problem, try changing the test data sizes (first line in Main
) and watch how the array gets reorganized on each run:
class Program
{
static void Main()
{
Point[] points = CreateTestData(1, 4).ToArray();
DisplayItems("Before", points);
Array.Sort(points, CompareByX);
DisplayItems("After", points);
Console.ReadLine();
}
private class Point
{
public int X { get; private set; }
public int Y { get; private set; }
public override string ToString()
{ return string.Format("({0},{1})", X, Y); }
public Point(int x, int y)
{ X = x; Y = y; }
}
private static int CompareByX(Point a, Point b)
{ return a.X - b.X; }
private static IEnumerable<Point> CreateTestData(int maxX, int maxY)
{
for (int x = 0; x <= 1; x++)
for (int y = 0; y <= 4; y++)
yield return new Point(x, y);
}
private static void DisplayItems(string msg, Point[] points)
{
Console.WriteLine(msg);
foreach (Point p in points)
Console.WriteLine(p.ToString());
Console.WriteLine();
}
}
Of course, if you extend the comparer delegate to include the Y coordinate, you will not have this problem:
private static int CompareByX(Point a, Point b)
{
if (a.X == b.X)
return a.Y - b.Y;
else
return a.X - b.X;
}