按两个值排序,优先考虑其中一个值

时间:2011-01-02 01:50:26

标签: javascript sorting

我如何按countyear值按升序优先排序count值,对这些数据进行排序?

//sort this
var data = [
    { count: '12', year: '1956' },
    { count: '1', year: '1971' },
    { count: '33', year: '1989' },
    { count: '33', year: '1988' }
];
//to get this
var data = [
    { count: '1', year: '1971' },
    { count: '12', year: '1956' },
    { count: '33', year: '1988' },
    { count: '33', year: '1989' },
];

7 个答案:

答案 0 :(得分:61)

See the jsfiddle

data.sort(function (x, y) {
    var n = x.count - y.count;
    if (n !== 0) {
        return n;
    }

    return x.year - y.year;
});

答案 1 :(得分:44)

一个简单的解决方案是:

data.sort(function (a, b) {
  return a.count - b.count || a.year - b.year;
});

这是有效的,因为如果 count 不同,那么排序就是基于此。如果 count 相同,则第一个表达式返回0,转换为 false ,并使用第二个表达式的结果(即排序基于 year < / em>的)。

答案 2 :(得分:13)

您可以使用JavaScript的.sort()数组方法(try it out):

data.sort(function(a, b) {
    // Sort by count
    var dCount = a.count - b.count;
    if(dCount) return dCount;

    // If there is a tie, sort by year
    var dYear = a.year - b.year;
    return dYear;
});

注意:这会更改原始数组。如果您需要先制作副本,可以这样做:

var dataCopy = data.slice(0);

答案 3 :(得分:6)

你必须像这样解决这个问题

var customSort = function(name, type){
     return function(o, p){
         var a, b;
         if(o && p && typeof o === 'object' && typeof p === 'object'){
            a = o[name];
            b = p[name];
           if(a === b){
              return typeof type === 'function' ? type(o, p) : o;
           }

           if(typeof a=== typeof b){
              return a < b ? -1 : 1;
            }
          return typeof a < typeof b ? -1 : 1;
        }
     };

};

例如:  data.sort(customSort('year',customSort('count')));

答案 4 :(得分:6)

基于优秀的@RobG solution,这是一个通用函数,可以使用JS2015在map + find上狡猾地排序多个不同的属性:

let sortBy = (p, a) => a.sort((i, j) => p.map(v => i[v] - j[v]).find(r => r))

sortBy(['count', 'year'], data)

此外,如果您愿意,还可以使用传统的JS版本(在旧浏览器中由于find compatibility而谨慎使用):

var sortBy = function (properties, targetArray) {
  targetArray.sort(function (i, j) {
    return properties.map(function (prop) {
      return i[prop] - j[prop];
    }).find(function (result) {
      return result;
    });
  });
};

答案 5 :(得分:1)

使用此处'count' - &gt;第一优先级和'年' - &gt;第二优先

data.sort(function(a,b){
  return a['count']<b['count']?-1:(a['count']>b['count']?1:(a['year']<b['year']?-1:1));
});

答案 6 :(得分:1)

如果您希望按字母顺序而不是数字对字符串进行排序,这里是一个示例问题及其解决方案。

示例问题:数组数组( finalArray ),第一个条目是文件夹路径,第二个条目是文件名;排序,以便数组首先按文件夹排列,并在相同的文件夹中按文件名排列。

E.g。排序后你期望:

[['folder1', 'abc.jpg'], 
 ['folder1', 'xyz.jpg'],
 ['folder2', 'def.jpg'],
 ['folder2', 'pqr.jpg']]

请参阅Array.prototype.sort() - compareFunction

finalArray.sort((x: any, y: any): number => {
  const folder1: string = x[0].toLowerCase();
  const folder2: string = y[0].toLowerCase();
  const file1: string = x[1].toLowerCase();
  const file2: string = y[1].toLowerCase();

  if (folder1 > folder2) {
    return 1;
  } else if (folder1 === folder2 && file1 > file2) {
    return 1;
  } else if (folder1 === folder2 && file1 === file2) {
    return 0;
  } else if (folder1 === folder2 && file1 < file2) {
    return -1;
  } else if (folder1 < folder2) {
    return -1;
  }
});

请记住,&#34; Z&#34;来之前&#34; a&#34; (资本首先根据 Unicode代码点)这就是为什么我有 toLowerCase()。上述实现没有解决的问题是&#34; 10abc&#34;将来之前&#34; 9abc&#34;。