js中 英文中文数字混合排序
问题简述:
Array本身有sort方法,但是实现不了中英文混合排序。
一、Array默认的排序
Array的默认排序
sort() 方法用原地算法对数组的元素进行排序,并返回数组。默认排序顺序是在将元素转换为字符串,然后比较它们的UTF-16代码单元值序列时构建的
let chinese = ['应用','服务器','张三','蓝天','随便什么吧']
chinese.sort()
console.log('chinese',chinese)
let english = ['zara','xxxx','test','what','banana','apple','pear','egg']
english.sort()
console.log('english',english)
结果如下:
这里的英文排序没有问题,但是中文排序就没有按照字母顺序进行排序。按照了中文字符串的 charCodeAt值进行从小到大的排序。 ‘应用’.charCodeAt() 为24212 ‘张三’.charCodeAt() 值为 24352
二、Array的sort中使用函数
sort的参数可以为一个比较函数,如果没有指明 compareFunction ,那么元素会按照转换为的字符串的诸个字符的Unicode值进行排序。例如 “Banana” 会被排列到 “cherry” 之前。当数字按由小到大排序时,9 出现在 80 之前,但因为(没有指明 compareFunction),比较的数字会先被转换为字符串,所以在Unicode顺序上 “80” 要比 “9” 要靠前。
如果指明了 compareFunction ,那么数组会按照调用该函数的返回值排序。即 a 和 b 是两个将要被比较的元素:
- 如果 compareFunction(a, b) 小于 0 ,那么 a 会被排列到 b 之前;
- 如果 compareFunction(a, b) 等于 0 , a 和 b 的相对位置不变;
- 如果 compareFunction(a, b) 大于 0 , b 会被排列到 a 之前。
compareFunction(a, b) 必须总是对相同的输入返回相同的比较结果,否则排序的结果将是不确定的。
这个对于数字比较有效。 默认的排序会将10 排在9之前
let numbers = [1,20,10,4,9,6]
numbers.sort((x,y)=>{
if(x>y){
return 1
}else if(x<y){
return -1
}else{
return 0
}
})
返回值为 [1, 4, 6, 9, 10, 20] 这样就可以按照数字大小正常排序了。
这里提一下一个很好的乱序方法,可以用sort加compareFunction实现。
sortNumbers.sort(()=>{
return Math.random()-0.5
})
三、localeCompare中文排序
localCompare是用本地特定的顺序来比较两个字符串。
stringObject.localeCompare(target)
如果 stringObject 小于 target,则 localeCompare() 返回小于 0 的数。如果 stringObject 大于 target,则该方法返回大于 0 的数。如果两个字符串相等,或根据本地排序规则没有区别,该方法返回 0。
let chinese2 = ['应用','服务器','张三','蓝天','随便什么吧']
chinese2.sort((x,y)=>{
return x.localeCompare(y)
})
结果为中文的正常排序
[“服务器”, “蓝天”, “随便什么吧”, “应用”, “张三”]
四、中英文排序
直接使用localCompare对中英文的结果 ,按照中文按照正常排序在前,英文在后,数字会报错。且顺序难以调整
如果要实现中英文一起的排序就需要把以上的方法组合使用。
let chineseAndEngAndNumber = ['应用','zoo','服务器','banana','pear','start','张三','蓝天','随便什么吧']
chineseAndEngAndNumber.sort((x,y)=>{
let reg = /[a-zA-Z0-9]/
if(reg.test(x)|| reg.test(y)){
if(x>y){
return 1
}else if(x<y){
return -1
}else{
return 0
}
}else{
return x.localeCompare(y)
}
})
结果是我们要的了。
[“banana”, “pear”, “start”, “zoo”, “服务器”, “蓝天”, “随便什么吧”, “应用”, “张三”]