按最接近1的值对数组进行排序

7

我需要对值数组进行排序。

var arr = [0.3, 0.76, 0.98, 1.12, 1.36, 1.9];

最接近1的值,将在上述示例中导致以下结果:

[0.98, 1.12, 0.76, 1.36, 0.3, 1.9];

我知道可以通过使用自定义排序函数来实现。

arr.sort(function(a, b){
    return b - a;
});

我可以控制sort()的工作方式,但是我不知道如何设计自定义函数使其按照期望的方式工作。

也许有人可以为我指点迷津。

3个回答

21

只需检查它们与1的距离。

arr.sort(function(a, b){
    return Math.abs(1-a) - Math.abs(1-b);
});

进一步解释一下,它计算两个数字与1之间的距离,例如:

  • a=-10b=4,它们到1的距离分别为11和3。函数返回一个正数,因此4会在排序后出现在-10之前。
  • a=-1b=4,它们到1的距离分别为2和3。函数返回一个负数,因此-1会在4之前出现在数组中。

如评论所请求,下面的修改将优先考虑小于1的值。

arr.sort(function(a, b){
    if(a<1 && b>=1){return -1;}
    if(a>=1 && b<1){return 1;}
    return (Math.abs(1-a) - Math.abs(1-b));
});

你能否详细说明一下,并展示如何进行调整,以便更偏好小于1的值而不是大于1的值? - SquareCat

1

如果您希望小于1的数字在排序时偏向于比大于1的等距离数字更低,请测试差值是否相等,如果相等,则修改其中一个值:

var arr = [1.02, 0.3, 0.76, 0.98, 1.12, 1.36, 1.9, 1.24];

// Unbiased
arr.sort(function(a, b){
    return Math.abs(1-a) - Math.abs(1-b);
});

console.log('unbiased: ' + arr); // unbiased: 1.02,0.98,1.12,0.76,1.24,1.36,0.3,1.9

var arr = [1.02, 0.3, 0.76, 0.98, 1.12, 1.36, 1.9, 1.24];

// Biased so numbers less than 1 sort higher than those greater than 1
// where their difference from 1 is equal
arr.sort(function(a, b) {
  var da = 1 - a;
  var db = 1 - b;

  da -= da < 0? 1e-14 : 0;
  db -= db < 0? 1e-14 : 0;

  return Math.abs(da) - Math.abs(db);
});

console.log('biased: ' + arr); // biased: 0.98,1.02,1.12,0.76,1.24,1.36,0.3,1.9

0

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接