Fla*_*nix 5 javascript sorting
我需要实现一个与 Array.prototype.sort 的默认比较函数具有相同行为的函数
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort
阅读文档后,我偶然发现了这一点:
默认排序顺序是根据字符串 Unicode 代码点。
这是什么意思?这是否意味着我将每个对象都转换为字符串?
如果是这样,假设我有数组[2, "a", { hello: "world" }]
,这些步骤是否正确?
[2, "a", { hello: "world" }]
为["2", "a", '{ hello: "world" }']
如何实现给定任何对象的比较函数,其行为与 sort 中的比较函数完全相同?
阅读ECMA规范:
我现在相信如果comparefn
是undefined
,那么他们使用这个算法作为默认值:
http://www.ecma-international.org/ecma-262/6.0/#sec-sortcompare
有人可以确认吗?
在阅读了 ECMA 规范并四处询问后,我找到了一个模拟chrome 中defaultCompare
默认行为的函数:Array.prototype.sort()
const defaultCompare = ( x, y ) => {
//INFO: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort
//ECMA specification: http://www.ecma-international.org/ecma-262/6.0/#sec-sortcompare
if( x === undefined && y === undefined )
return 0;
if( x === undefined )
return 1;
if( y === undefined )
return -1;
const xString = toString(x);
const yString = toString(y);
if( xString < yString )
return -1;
if( xString > yString )
return 1;
return 0;
};
const toString = obj => {
//ECMA specification: http://www.ecma-international.org/ecma-262/6.0/#sec-tostring
if( obj === null )
return "null";
if( typeof obj === "boolean" || typeof obj === "number" )
return (obj).toString();
if( typeof obj === "string" )
return obj;
if( typeof obj === "symbol" )
throw new TypeError();
//we know we have an object. perhaps return JSON.stringify?
return (obj).toString();
};
module.exports = defaultCompare;
Run Code Online (Sandbox Code Playgroud)
您可以像下面这样测试这个函数:
const arr = [ undefined, null, 3, 2, 'B', 'a', 'b', 'A',
{ hello: "world"}, { goodnight: 'moon'} ]
assertEql( arr.sort(), arr.sort(defaultCompare) ); //true
Run Code Online (Sandbox Code Playgroud)
如果您在同一浏览器中测试它们,则输出应该相同。