前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >JavaScript中数组排序sort深入理解(Array.prototype.sort)

JavaScript中数组排序sort深入理解(Array.prototype.sort)

作者头像
从入门到进错门
发布2018-12-19 16:40:56
7270
发布2018-12-19 16:40:56
举报

疑问

最近在看算法书的时候看到C++中的sort方法,书中介绍是使用的快速排序。于是想起来自己天天都在写的JavaScript中的sort排序,它使用的是什么排序算法呢?各个浏览器使用的是同一种排序算法吗?

带着问题,打开了ECMA官方规范

ECMA 2015 ECMA 2016 ECMA 2017

规范中并没有写明具体使用的排序算法,只是说了JavaScript的sort方法(Array.prototype.sort)并不一定稳定!

Google Chrome浏览器

Google的Chrome浏览器的JavaScript引擎是:V8。

既然ECMA没有规定具体的排序算法,那具体实施应该是各个JavaScript引擎决定了。于是打开Chrome V8引擎的官方源码,V8引擎github源码

第239行到254行:

code:

代码语言:javascript
复制
function InnerArraySort(array, length, comparefn) {
  // In-place QuickSort algorithm.
  // For short (length <= 10) arrays, insertion sort is used for efficiency.
  if (!IS_CALLABLE(comparefn)) {
    comparefn = function (x, y) {
      if (x === y) return 0;
      if (%_IsSmi(x) && %_IsSmi(y)) {
        return %SmiLexicographicCompare(x, y);
      }
      x = TO_STRING(x);
      y = TO_STRING(y);
      if (x == y) return 0;
      else return x < y ? -1 : 1;
    };
}

代码中的注释明确写着:这个地方使用快速排序,但是当长度小于11的数组,使用的是插入排序。这也符合我们的正常观点,因为插入排序在数组长度小于一定值的时候是会比快速排序速度更快,快速排序在大规模数据的时候更有优势。插入排序是稳定的,快速排序是不稳定的。

知道了Chrome浏览器的排序算法。其他浏览器是不是也是这样呢?我们接着看。

Mozilla Firefox浏览器

Mozilla的Firefox浏览器的JavaScript引擎是:SpiderMonkey。

然后同样的方法,我们直接去看源码。源码地址

第2306行的注释:

code:

代码语言:javascript
复制
 /*
     * We need a temporary array of 2 * len Value to hold the array elements
     * and the scratch space for merge sort. Check that its size does not
     * overflow size_t, which would allow for indexing beyond the end of the
     * malloc'd vector.
     */

Mozilla的Firefox浏览器使用的是归并排序,归并排序是稳定的。

Safari浏览器

Safari浏览器的JavaScript引擎是:Nitro(JavaScriptCore )。

源码地址

第579行开始是这样写的:

code:

代码语言:javascript
复制
function comparatorSort(array, length, comparator){
    let valueCount = compact(array, length);
    mergeSort(array, valueCount, comparator); // 归并排序
}

function stringSort(array, length){
    let valueCount = compact(array, length);
    let strings = @newArrayWithSize(valueCount);
    for (let i = 0; i < valueCount; ++i)
        strings[i] = { string: @toString(array[i]), value: array[i] };
    bucketSort(array, 0, strings, 0); // 桶排序
}

Safari浏览器使用的是桶排序和归并排序,如果参数中含有comparator函数就使用归并排序,没有的话就使用桶排序。桶排序的稳定性不确定,归并排序是稳定的。

Microsoft Edge和IE浏览器

最后再来看看我们最难伺候的老大哥,老大哥浏览器的JavaScript引擎是:Chakra。

源码地址

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2018年11月28日,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 疑问
  • Google Chrome浏览器
  • Mozilla Firefox浏览器
  • Safari浏览器
  • Microsoft Edge和IE浏览器
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档