//
Divide: Partition (rearrange) the array A[p ‥ r] into two (possibly empty) subarrays A[p ‥ q - 1]
// and A[q + 1 ‥ r] such that each element of A[p ‥ q - 1] is less than or equal to A[q], which is, in turn,
// less than or equal to each element of A[q + 1 ‥ r]. Compute the index q as part of this partitioning procedure.
// Conquer: Sort the two subarrays A[p ‥ q -1] and A[q +1 ‥ r] by recursive calls to quicksort.
// Combine: Since the subarrays are sorted in place, no work is needed to combine them: the entire array A[p ‥ r] is now sorted.
namespace FengChen.Practices
{
namespace Chapter7
{
public class QuickSort
{
private static bool m_NonDecreasing;
private static bool Ordered(Int32 A, Int32 B)
{
if (m_NonDecreasing) return (A <= B);
else return (A >= B);
}
private static void QuicksortDriver(Int32[] A, Int32 p, Int32 r)
{
if (p >= r) return;
Int32 q = Partition(A, p, r);
QuicksortDriver(A, p, q - 1);
QuicksortDriver(A, q + 1, r);
}
private static Int32 Partition(Int32[] A, Int32 p, Int32 r)
{
Int32 x = A[r]; // pivot
Int32 i = p - 1;
for (Int32 j = p; j < r; j++)
if (Ordered(A[j], x)) Common.Exchange(ref A[++i], ref A[j]);
Common.Exchange(ref A[++i], ref A[r]);
return i;
}
/// <summary>
/// Sort the array to non decreasing order
/// </summary>
/// <param name="InputArray"></param>
public static void Sort(Int32[] InputArray, bool Increasing)
{
m_NonDecreasing = Increasing;
QuicksortDriver(InputArray, 0, InputArray.Length - 1);
}
}
}
}
// and A[q + 1 ‥ r] such that each element of A[p ‥ q - 1] is less than or equal to A[q], which is, in turn,
// less than or equal to each element of A[q + 1 ‥ r]. Compute the index q as part of this partitioning procedure.
// Conquer: Sort the two subarrays A[p ‥ q -1] and A[q +1 ‥ r] by recursive calls to quicksort.
// Combine: Since the subarrays are sorted in place, no work is needed to combine them: the entire array A[p ‥ r] is now sorted.
namespace FengChen.Practices
{
namespace Chapter7
{
public class QuickSort
{
private static bool m_NonDecreasing;
private static bool Ordered(Int32 A, Int32 B)
{
if (m_NonDecreasing) return (A <= B);
else return (A >= B);
}
private static void QuicksortDriver(Int32[] A, Int32 p, Int32 r)
{
if (p >= r) return;
Int32 q = Partition(A, p, r);
QuicksortDriver(A, p, q - 1);
QuicksortDriver(A, q + 1, r);
}
private static Int32 Partition(Int32[] A, Int32 p, Int32 r)
{
Int32 x = A[r]; // pivot
Int32 i = p - 1;
for (Int32 j = p; j < r; j++)
if (Ordered(A[j], x)) Common.Exchange(ref A[++i], ref A[j]);
Common.Exchange(ref A[++i], ref A[r]);
return i;
}
/// <summary>
/// Sort the array to non decreasing order
/// </summary>
/// <param name="InputArray"></param>
public static void Sort(Int32[] InputArray, bool Increasing)
{
m_NonDecreasing = Increasing;
QuicksortDriver(InputArray, 0, InputArray.Length - 1);
}
}
}
}
这个实现倒并不难。可是请看算法导论后面的一个习题:
What value of q does PARTITION return when all elements in the array A [ p ‥ r ] have the same value? Modify PARTITION so that q = ( p + r )/2 when all elements in the array A [ p ‥ r ] have the same value.
后面 的疑问目前我研究看来没有不极大伤害性能的解答。