飞镖排序方法中使用的算法是什么?

时间:2020-02-20 03:32:47

标签: dart

我发现dart语言在List类中具有内置的sort方法,我想知道他们在此方法中使用的算法是什么,以及Big O表示法是什么?

2 个答案:

答案 0 :(得分:3)

我发现dart语言在List类中具有内置的sort方法,我想知道他们在此方法中使用的算法是什么,以及Big O表示法是什么?

如果我们查看一下SDK,可以在sort上找到List方法的以下实现:

  void sort([int compare(E a, E b)]) {
    Sort.sort(this, compare ?? _compareAny);
  }

https://github.com/dart-lang/sdk/blob/b86c6e0ce93e635e3434935e31fac402bb094705/sdk/lib/collection/list.dart#L340-L342

仅将排序转发到以下内部帮助程序类:

https://github.com/dart-lang/sdk/blob/a75ffc89566a1353fb1a0f0c30eb805cc2e8d34c/sdk/lib/internal/sort.dart

关于排序算法有以下评论:

/**
 * Dual-Pivot Quicksort algorithm.
 *
 * This class implements the dual-pivot quicksort algorithm as presented in
 * Vladimir Yaroslavskiy's paper.
 *
 * Some improvements have been copied from Android's implementation.
 */

这种排序算法实际上与Java(至少Java 7)中使用的算法相同:

http://www.docjar.com/html/api/java/util/DualPivotQuicksort.java.html

在这里我们可以看到O标记主要是O(n log(n))

    * This class implements the Dual-Pivot Quicksort algorithm by
    * Vladimir Yaroslavskiy, Jon Bentley, and Josh Bloch. The algorithm
    * offers O(n log(n)) performance on many data sets that cause other
    * quicksorts to degrade to quadratic performance, and is typically
    * faster than traditional (one-pivot) Quicksort implementations.

有关更多详细信息,您可以阅读Dual-Pivot Quicksort算法设计者的论文:

https://web.archive.org/web/20151002230717/http://iaroslavski.narod.ru/quicksort/DualPivotQuicksort.pdf

但是,还请注意,Dart还具有以下常量:

  // When a list has less then [:_INSERTION_SORT_THRESHOLD:] elements it will
  // be sorted by an insertion sort.
  static const int _INSERTION_SORT_THRESHOLD = 32;
...
  static void _doSort<E>(
      List<E> a, int left, int right, int compare(E a, E b)) {
    if ((right - left) <= _INSERTION_SORT_THRESHOLD) {
      _insertionSort(a, left, right, compare);
    } else {
      _dualPivotQuicksort(a, left, right, compare);
    }
  }

因此对于小列表,使用传统的插入排序算法更有意义,该算法的最坏情况下的大O为О(n^2)。但是,由于输入量很小,因此它比Dual-Pivot Quicksort算法要合适。

答案 1 :(得分:0)

https://dartpad.dartlang.org/,尝试以下代码。我无法回答您有关幕后实现的问题,但您可以打赌它是O(n log n)。

我使用答案是因为我无法轻松地在注释中提供代码。

void main() {
  Map<String, int> map = {'a': 1, 'b': 2};

  List<String> list = ['banana', 'apple', 'age', 'bob'];

  list.sort((String a, String b) => a.compareTo(b));
  print(list);
}

BTW list.sort();将给出相同的结果,因为该自定义比较器与默认比较器相同。

相关问题