quicksort 快速排序 quick sort
* Java基本版
package cn.mediamix; import java.util.LinkedList; public class QuickSort { public static void qsort(int[]a) { _qsort(a, 0, a.length-1); } private static void _qsort(int []a, int low, int high) { if (low >= high) { return; } int first = low, last = high, pivot = a[first]; while (first < last) { while (first < last && a[last] >= pivot) { --last; } a[first] = a[last]; while (first < last && pivot >= a[first]) { ++first; } a[last] = a[first]; } a[first] = pivot; _qsort(a, low, first-1); _qsort(a, first+1, high); } public static void main(String[] args) { int[] a = {9, 1, 4, 7, 8, 0, 6, 5, 2, 3}; qsort(a); // 测试新的遍历方式 LinkedList<Integer> items = new LinkedList<Integer>(); for (int e : a) { items.add(new Integer(e)); } items.forEach(item->System.out.println(item)); } }
* Java通用版排序
GenericSort.java
package cn.mediamix; import java.util.Comparator; import java.util.List; public class GenericSort<T> { public static <T> void qsort(List<T> a, Comparator<T> comparator) { _qsort(a, 0, a.size() - 1, comparator); } private static <T> void _qsort(List<T> a, int low, int high, Comparator<T> comparator) { if (low >= high) { return; } int first = low, last = high; T pivot = a.get(first); while (first < last) { while (first < last && comparator.compare(a.get(last), pivot) >= 0) { --last; } a.set(first, a.get(last)); while (first < last && comparator.compare(pivot, a.get(first)) >= 0) { ++first; } a.set(last, a.get(first)); } a.set(first, pivot); _qsort(a, low, first - 1, comparator); _qsort(a, first + 1, high, comparator); } }
TestGeneric.java
package cn.mediamix; import java.util.ArrayList; import java.util.Comparator; import java.util.LinkedList; import java.util.List; import cn.mediamix.GenericSort; public class TestGeneric { public static void main(String[] args) { int[] a = {9, 1, 4, 7, 8, 0, 6, 5, 2, 3}; // int[] => List<Integer> List<Integer> items = new ArrayList<Integer>(a.length); for (int e : a) { items.add(new Integer(e)); } // my qsort GenericSort.qsort(items, new Comparator<Integer>() { @Override public int compare(Integer i1, Integer i2) { return i2-i1; // 从大到小排序 } }); // traverse items.forEach(item -> {System.out.println(item);}); // test string List<String> greet = new LinkedList<String>(); greet.add("Hello"); greet.add("Bonjour"); greet.add("Shalom"); greet.add("Hola"); greet.add("Konnichiwa"); greet.add("Nihao"); GenericSort.qsort(greet, new Comparator<String>() { @Override public int compare(String s1, String s2) { return s1.compareTo(s2); } }); greet.forEach(item -> {System.out.println(item);}); } }
Output:
9 8 7 6 5 4 3 2 1 0 Bonjour Hello Hola Konnichiwa Nihao Shalom
参考代码片段
Collections.sort(list, new Comparator<Dog>() { @Override public int compare(Dog o1, Dog o2) { return o2.age - o1.age; } });
@file: java.util.collections
public class Collections {
// ...
public static <T> void sort(List<T> list, Comparator<? super T> c) {
list.sort(c);
}
//...
}
@file: java.util.List
public interface List<E> extends Collection<E> {
// ...
@SuppressWarnings({"unchecked", "rawtypes"})
default void sort(Comparator<? super E> c) {
Object[] a = this.toArray();
Arrays.sort(a, (Comparator) c);
ListIterator<E> i = this.listIterator();
for (Object e : a) {
i.next();
i.set((E) e);
}
}
// ...
}
@file: java.util.comparator
public interface Comparator<T> {
// ...
int compare(T o1, T o2);
}
//-------------------------------------------------------------------------//
// 下面的是弱类型的脚本语言: //
// ----------------------------------------------------------------------------------------//
* javascript
// 上一次写错了 first < last 对于下标比较大小,控制下标走动位置,不需要用比较大小的回调函数
/** * Created by Mch on 8/5/18. */ function qsort(a, c) { c = c || function(a, b) { return a - b; }; function _qsort(a, low, high) { if (low >= high) { return; } var first = low, last = high, pivot = a[first]; while (first < last) { while (first < last && c(a[last], pivot) >= 0) { --last; } a[first] = a[last]; while (first < last && c(pivot, a[first]) >= 0) { ++first; } a[last] = a[first]; } a[first] = pivot; _qsort(a, low, first-1); _qsort(a, first+1, high); } return _qsort(a, 0, a.length-1); }
test:
var a = [9, 1, 4, 7, 8, 0, 6, 5, 2, 3]; qsort(a, function(a, b) { return b-a; }); console.log(a); var b = ['Hello', 'wold', 'sange', 'yasha', 'shuriken', 'sword']; qsort(b, function(a, b) { return a.localeCompare(b); }); console.log(b);
output:
[ 9, 8, 7, 6, 5, 4, 3, 2, 1, 0 ] [ 'Hello', 'sange', 'shuriken', 'sword', 'wold', 'yasha' ]
* PHP:
http://php.net/manual/en/function.usort.php
bool usort ( array &$array , callable $value_compare_func )
<?php class QuickSort { private $compare; public function __construct($compare) { if (!$compare) { $compare = function($a, $b) { return $a - $b; }; } $this->compare = $compare; } private function _qsort(&$a, $low, $high) { if ($low >= $high) { return; } $first = $low; $last = $high; $pivot = $a[$first]; $c = $this->compare; $ge = function($a, $b) use ($c) { return call_user_func($c, $a, $b) >= 0; }; while ($first < $last) { while ($first < $last && $ge($a[$last], $pivot)) { --$last; } $a[$first] = $a[$last]; while ($first < $last && $ge($pivot, $a[$first])) { ++$first; } $a[$last] = $a[$first]; } $a[$first] = $pivot; self::_qsort($a, $low, $first-1); self::_qsort($a, $first+1, $high); } public function qsort(&$a) { self::_qsort($a, 0, count($a)-1); } }
test:
<?php // test: "Hello world Blog Control" 字符串按空格分隔,分成数组,转化为小写,按字母顺序排 $a = explode(" ", "Hello world Blog Control"); $a = array_map(function($e) { return strtolower($e); }, $a); $q = new QuickSort(function($a, $b) { return strcmp($a, $b); }); $q->qsort($a); // 这里用call_user_func($q->qsort, $a)不起作用? print_r($a);
Output:
Array
(
[0] => blog
[1] => control
[2] => hello
[3] => world
)
快速排序算法