Quick Sort implementation in Java
Quick Sort implementation
public class Main{
public static void main(String[] args) {
int maxSize = 16; // array size
QuickSortSimpleVersion arr = new QuickSortSimpleVersion(maxSize); // create array
// w w w .j a va 2 s . c om
for (int j = 0; j < maxSize; j++){
long n = (int) (java.lang.Math.random() * 99);
arr.insert(n);
}
arr.display();
arr.quickSort();
arr.display();
}
}
class QuickSortSimpleVersion {
private long[] data;
private int len;
public QuickSortSimpleVersion(int max) {
data = new long[max];
len = 0;
}
public void insert(long value) {
data[len] = value;
len++;
}
public void display() {
System.out.print("Data:");
for (int j = 0; j < len; j++)
System.out.print(data[j] + " ");
System.out.println("");
}
public void quickSort() {
recQuickSort(0, len - 1);
}
public void recQuickSort(int left, int right) {
if (right - left <= 0){ // if size <= 1 already sorted
return;
}else{ // size is 2 or larger
long pivot = data[right]; // rightmost item
// partition range
int partition = partitionData(left, right, pivot);
recQuickSort(left, partition - 1); // sort left side
recQuickSort(partition + 1, right); // sort right side
}
}
public int partitionData(int left, int right, long pivot) {
int leftPtr = left - 1; // left (after ++)
int rightPtr = right; // right-1 (after --)
while (true) { // find bigger item
while (data[++leftPtr] < pivot){
;
}
// find smaller item
while (rightPtr > 0 && data[--rightPtr] > pivot){
;
}
if (leftPtr >= rightPtr){ // if pointers cross, partition done
break;
}else{
swap(leftPtr, rightPtr);
}
}
swap(leftPtr, right); // restore pivot and return pivot location
return leftPtr;
}
public void swap(int d1, int d2) {
long temp = data[d1];
data[d1] = data[d2];
data[d2] = temp;
}
}
The code above generates the following result.
Quick Sort implementation from jodd.org
The following quick sort code is from joddy.org and released under open source license.
// Copyright (c) 2003-2009, Jodd Team (jodd.org). All Rights Reserved.
//from ww w . ja v a2s.com
import java.util.Arrays;
import java.util.Collections;
import java.util.Comparator;
public class Main{
public static void main(String[] argv){
Object[] objectArray = new Integer[]{1,2,3};
FastQuickSort.qsort(objectArray, Collections.reverseOrder());
System.out.println(Arrays.toString(objectArray));
}
}
/**
* Maybe the fastest implementation of famous Quick-Sort
* algorithm. It is even faster than Denisa Ahrensa implementation that
* performs 7.5s for sorting million objects, this implementation
* sorts for 6.8s. However, {@link FastMergeSort} is much faster.
*/
class FastQuickSort {
@SuppressWarnings({"unchecked"})
public static void qsort(Object[] c, Comparator comparator) {
int i, j, left = 0, right = c.length - 1, stack_pointer = -1;
int[] stack = new int[128];
Object swap, temp;
while (true) {
if (right - left <= 7) {
for (j = left + 1; j <= right; j++) {
swap = c[j];
i = j - 1;
while (i >= left && comparator.compare(c[i], swap) > 0) {
c[i + 1] = c[i--];
}
c[i + 1] = swap;
}
if (stack_pointer == -1) {
break;
}
right = stack[stack_pointer--];
left = stack[stack_pointer--];
} else {
int median = (left + right) >> 1;
i = left + 1;
j = right;
swap = c[median]; c[median] = c[i]; c[i] = swap;
if (comparator.compare(c[left], c[right]) > 0) {
swap = c[left]; c[left] = c[right]; c[right] = swap;
}
if (comparator.compare(c[i], c[right]) > 0) {
swap = c[i]; c[i] = c[right]; c[right] = swap;
}
if (comparator.compare(c[left], c[i]) > 0) {
swap = c[left]; c[left] = c[i]; c[i] = swap;
}
temp = c[i];
while (true) {
//noinspection ControlFlowStatementWithoutBraces,StatementWithEmptyBody
while (comparator.compare(c[++i], temp) < 0);
//noinspection ControlFlowStatementWithoutBraces,StatementWithEmptyBody
while (comparator.compare(c[--j], temp) > 0);
if (j < i) {
break;
}
swap = c[i]; c[i] = c[j]; c[j] = swap;
}
c[left + 1] = c[j];
c[j] = temp;
if (right - i + 1 >= j - left) {
stack[++stack_pointer] = i;
stack[++stack_pointer] = right;
right = j - 1;
} else {
stack[++stack_pointer] = left;
stack[++stack_pointer] = j - 1;
left = i;
}
}
}
}
}
The code above generates the following result.
QuickSort dealing with small amount of elements
The following code is an open source version of quick sort. The interesting part of it is that it checks the number of elements in the array. If there are only three elements in the array it would not use the quick sort algorithm which will take longer time and more resource.
/*/*from w w w.j a va2 s . c om*/
* Copyright (c) 1998 - 2005 Versant Corporation
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Versant Corporation - initial API and implementation
*/
import java.util.Comparator;
/**
* Quicksort implementation for sorting arrays. Unlike the merge sort in
* java.utils.Collections this one does not create any objects. There are
* two implementations, one for arrays of Comparable's and another that
* uses a comparator.
*/
class Quicksort {
/**
* Sort the first size entries in a.
*/
public static void quicksort(Object[] a, int size) {
quicksort(a, 0, size - 1);
}
/**
* Sort the entries in a between left and right inclusive.
*/
public static void quicksort(Object[] a, int left, int right) {
int size = right - left + 1;
switch (size) {
case 0:
case 1:
break;
case 2:
if (compare(a[left], a[right]) > 0) swap(a, left, right);
break;
case 3:
if (compare(a[left], a[right - 1]) > 0) swap(a, left, right - 1);
if (compare(a[left], a[right]) > 0) swap(a, left, right);
if (compare(a[left + 1], a[right]) > 0) swap(a, left + 1, right);
break;
default:
int median = median(a, left, right);
int partition = partition(a, left, right, median);
quicksort(a, left, partition - 1);
quicksort(a, partition + 1, right);
}
}
private static int compare(Object a, Object b) {
if (a == null) {
return b == null ? 0 : -1;
} else if (b == null) {
return +1;
} else {
return ((Comparable)a).compareTo(b);
}
}
private static void swap(Object[] a, int left, int right) {
Object t = a[left];
a[left] = a[right];
a[right] = t;
}
private static int median(Object[] a, int left, int right) {
int center = (left + right) / 2;
if (compare(a[left], a[center]) > 0) swap(a, left, center);
if (compare(a[left], a[right]) > 0) swap(a, left, right);
if (compare(a[center], a[right]) > 0) swap(a, center, right);
swap(a, center, right - 1);
return right - 1;
}
private static int partition(Object[] a, int left, int right, int pivotIndex) {
int leftIndex = left;
int rightIndex = right - 1;
while (true) {
while (compare(a[++leftIndex], a[pivotIndex]) < 0);
while (compare(a[--rightIndex], a[pivotIndex]) > 0);
if (leftIndex >= rightIndex) {
break; // pointers cross so partition done
} else {
swap(a, leftIndex, rightIndex);
}
}
swap(a, leftIndex, right - 1); // restore pivot
return leftIndex; // return pivot location
}
/**
* Sort the first size entries in a.
*/
public static void quicksort(Object[] a, int size, Comparator c) {
quicksort(a, 0, size - 1, c);
}
/**
* Sort the entries in a between left and right inclusive.
*/
public static void quicksort(Object[] a, int left, int right, Comparator c) {
int size = right - left + 1;
switch (size) {
case 0:
case 1:
break;
case 2:
if (c.compare(a[left], a[right]) > 0) swap(a, left, right);
break;
case 3:
if (c.compare(a[left], a[right - 1]) > 0) swap(a, left, right - 1);
if (c.compare(a[left], a[right]) > 0) swap(a, left, right);
if (c.compare(a[left + 1], a[right]) > 0) swap(a, left + 1, right);
break;
default:
int median = median(a, left, right, c);
int partition = partition(a, left, right, median, c);
quicksort(a, left, partition - 1, c);
quicksort(a, partition + 1, right, c);
}
}
private static int median(Object[] a, int left, int right, Comparator c) {
int center = (left + right) / 2;
if (c.compare(a[left], a[center]) > 0) swap(a, left, center);
if (c.compare(a[left], a[right]) > 0) swap(a, left, right);
if (c.compare(a[center], a[right]) > 0) swap(a, center, right);
swap(a, center, right - 1);
return right - 1;
}
private static int partition(Object[] a, int left, int right,
int pivotIndex, Comparator c) {
int leftIndex = left;
int rightIndex = right - 1;
while (true) {
while (c.compare(a[++leftIndex], a[pivotIndex]) < 0);
while (c.compare(a[--rightIndex], a[pivotIndex]) > 0);
if (leftIndex >= rightIndex) {
break; // pointers cross so partition done
} else {
swap(a, leftIndex, rightIndex);
}
}
swap(a, leftIndex, right - 1); // restore pivot
return leftIndex; // return pivot location
}
}
Quick sort with median-of-three partitioning
public class Main {
private long[] data;
//from w w w.j a v a 2s .com
private int len;
public Main(int max) {
data = new long[max];
len = 0;
}
public void insert(long value) {
data[len] = value; // insert and increment size
len++;
}
public void display() {
System.out.print("Data:");
for (int j = 0; j < len; j++)
System.out.print(data[j] + " ");
System.out.println("");
}
public void quickSort() {
recQuickSort(0, len - 1);
}
public void recQuickSort(int left, int right) {
int size = right - left + 1;
if (size <= 3) // manual sort if small
manualSort(left, right);
else // quicksort if large
{
long median = medianOf3(left, right);
int partition = partitionIt(left, right, median);
recQuickSort(left, partition - 1);
recQuickSort(partition + 1, right);
}
}
public long medianOf3(int left, int right) {
int center = (left + right) / 2;
// order left & center
if (data[left] > data[center])
swap(left, center);
// order left & right
if (data[left] > data[right])
swap(left, right);
// order center & right
if (data[center] > data[right])
swap(center, right);
swap(center, right - 1); // put pivot on right
return data[right - 1]; // return median value
}
public void swap(int dex1, int dex2) {
long temp = data[dex1];
data[dex1] = data[dex2];
data[dex2] = temp;
}
public int partitionIt(int left, int right, long pivot) {
int leftPtr = left; // right of first elem
int rightPtr = right - 1; // left of pivot
while (true) {
// find bigger
while (data[++leftPtr] < pivot)
;
// find smaller
while (data[--rightPtr] > pivot)
;
if (leftPtr >= rightPtr) // if pointers cross, partition done
break;
else
// not crossed, so
swap(leftPtr, rightPtr); // swap elements
}
swap(leftPtr, right - 1); // restore pivot
return leftPtr; // return pivot location
}
public void manualSort(int left, int right) {
int size = right - left + 1;
if (size <= 1)
return; // no sort necessary
if (size == 2) { // 2-sort left and right
if (data[left] > data[right])
swap(left, right);
return;
} else // size is 3
{ // 3-sort left, center, & right
if (data[left] > data[right - 1])
swap(left, right - 1); // left, center
if (data[left] > data[right])
swap(left, right); // left, right
if (data[right - 1] > data[right])
swap(right - 1, right); // center, right
}
}
public static void main(String[] args) {
int maxSize = 16;
Main arr = new Main(maxSize);
for (int j = 0; j < maxSize; j++) { // random numbers
long n = (int) (java.lang.Math.random() * 99);
arr.insert(n);
}
arr.display();
arr.quickSort();
arr.display();
}
}
The code above generates the following result.