2011-05-25 23 views
37
grouperArray.sort(function (a, b) { 
    var aSize = a.gsize; 
    var bSize = b.gsize; 
    var aLow = a.glow; 
    var bLow = b.glow; 
    console.log(aLow + " | " + bLow);  
    return (aSize < bSize) ? -1 : (aSize > bSize) ? 1 : 0; 
}); 

Así que el código anterior ordena la matriz por gsize - del más pequeño al más grande. Funciona bien Pero si el tamaño de gsize es el mismo, me gustaría que lo ordenara por brillo.Javascript ordena la matriz por dos campos

Gracias.

+0

la función de clasificación reacciona en el resultado positivo, negativo o cero. para que pueda escribir: "return aSize - bSize". será un código más simple y legible. –

Respuesta

51
grouperArray.sort(function (a, b) { 
    var aSize = a.gsize; 
    var bSize = b.gsize; 
    var aLow = a.glow; 
    var bLow = b.glow; 
    console.log(aLow + " | " + bLow); 

    if(aSize == bSize) 
    { 
     return (aLow < bLow) ? -1 : (aLow > bLow) ? 1 : 0; 
    } 
    else 
    { 
     return (aSize < bSize) ? -1 : 1; 
    } 
}); 
+0

Gracias. Realmente estaba luchando por ordenar en múltiples campos. – Maximus

3
grouperArray.sort(function (a, b) { 
    var aSize = a.gsize; 
    var bSize = b.gsize; 
    var aLow = a.glow; 
    var bLow = b.glow; 
    console.log(aLow + " | " + bLow);  
    return (aSize < bSize) ? -1 : (aSize > bSize) ? 1 : ((aLow < bLow) ? -1 : (aLow > bLow) ? 1 : 0); 
}); 
3
grouperArray.sort(function (a, b) { 
    var aSize = a.gsize;  
    var bSize = b.gsize;  
    var aLow = a.glow; 
    var bLow = b.glow; 
    console.log(aLow + " | " + bLow); 
    return (aSize < bSize) ? -1 : (aSize > bSize) ? 1 : (aLow < bLow) ? -1 : (aLow > bLow) ? 1 : 0); }); 
0
grouperArray.sort(function (a, b) { 
    var aSize = a.gsize; 
    var bSize = b.gsize; 
    if (aSize !== aSize) 
     return aSize - bSize; 
    return a.glow - b.glow; 
}); 

no probado, pero creo que debería funcionar.

6

Espero que el operador ternary((aSize < bSize) ? -1 : (aSize > bSize) ? 1 : 0;) te haya confundido. Debería revisar el enlace para entenderlo mejor.

Hasta entonces, aquí está su código explotado en if/else completo.

grouperArray.sort(function (a, b) { 
    if (a.gsize < b.gsize) 
    { 
     return -1; 
    } 
    else if (a.gsize > b.gsize) 
    { 
     return 1; 
    } 
    else 
    { 
     if (a.glow < b.glow) 
     { 
      return -1; 
     } 
     else if (a.glow > b.glow) 
     { 
      return 1; 
     } 
     return 0; 
    } 
}); 
0
grouperArray.sort(
    function(a,b){return a.gsize == b.gsize ? a.glow - b.glow : a.gsize - b.gsize} 
); 
0

Esto es lo que yo uso

function sort(a, b) { 
    var _a = "".concat(a.size, a.glow); 
    var _b = "".concat(b.size, b.glow); 
    return _a < _b; 
} 

concat los dos elementos en forma de cadena y que se ordenarán por un valor de cadena. Si lo desea, podría envolver _a y _b con parseInt para compararlos como números si sabe que serán numéricos.

5

Me doy cuenta de que esto fue preguntado hace un tiempo, pero pensé en agregar mi solución.

Esta función genera métodos de clasificación de forma dinámica. simplemente suministre cada nombre de propiedad de niño ordenable, antepuesto con +/- para indicar el orden ascendente o descendente. Súper reutilizable, y no necesita saber nada sobre la estructura de datos que ha reunido. Podría hacerse a prueba de idiotas, pero no parece necesario.

function getSortMethod(){ 
    var _args = Array.prototype.slice.call(arguments); 
    return function(a, b){ 
     for(var x in _args){ 
      var ax = a[_args[x].substring(1)]; 
      var bx = b[_args[x].substring(1)]; 
      var cx; 

      ax = typeof ax == "string" ? ax.toLowerCase() : ax/1; 
      bx = typeof bx == "string" ? bx.toLowerCase() : bx/1; 

      if(_args[x].substring(0,1) == "-"){cx = ax; ax = bx; bx = cx;} 
      if(ax != bx){return ax < bx ? -1 : 1;} 
     } 
    } 
} 

Ejemplo de uso:

Items.Sort (getSortMethod ('- precio', '+ prioridad', '+ nombre'));

esto ordenaría items con el más bajo price primero, con los vínculos que van al artículo con el priority más alto. más lazos se rompen por el elemento name

donde los artículos es una matriz como:

var items = [ 
    { name: "z - test item", price: "99.99", priority: 0, reviews: 309, rating: 2 }, 
    { name: "z - test item", price: "1.99", priority: 0, reviews: 11, rating: 0.5 }, 
    { name: "y - test item", price: "99.99", priority: 1, reviews: 99, rating: 1 }, 
    { name: "y - test item", price: "0", priority: 1, reviews: 394, rating: 3.5 }, 
    { name: "x - test item", price: "0", priority: 2, reviews: 249, rating: 0.5 } ... 
]; 

demostración en vivo: http://gregtaff.com/misc/multi_field_sort/

EDIT: Solucionado el problema con Chrome.

+0

¡Solución fantástica! :) – giorgio79

43
grouperArray.sort(function (a, b) { 
    return a.gsize - b.gsize || a.glow - b.glow; 
}); 

más corta versión

2

Aquí es una implementación para aquellos que quieran algo más genérico que funcionaría con cualquier número de campos.

Array.prototype.sortBy = function (propertyName, sortDirection) { 

    var sortArguments = arguments; 
    this.sort(function (objA, objB) { 

     var result = 0; 
     for (var argIndex = 0; argIndex < sortArguments.length && result === 0; argIndex += 2) { 

      var propertyName = sortArguments[argIndex]; 
      result = (objA[propertyName] < objB[propertyName]) ? -1 : (objA[propertyName] > objB[propertyName]) ? 1 : 0; 

      //Reverse if sort order is false (DESC) 
      result *= !sortArguments[argIndex + 1] ? 1 : -1; 
     } 
     return result; 
    }); 

} 

Básicamente, puede especificar cualquier número de propiedad de dirección Nombre/tipo:

var arr = [{ 
    LastName: "Doe", 
    FirstName: "John", 
    Age: 28 
}, { 
    LastName: "Doe", 
    FirstName: "Jane", 
    Age: 28 
}, { 
    LastName: "Foo", 
    FirstName: "John", 
    Age: 30 
}]; 

arr.sortBy("LastName", true, "FirstName", true, "Age", false); 
//Will return Jane Doe/John Doe/John Foo 

arr.sortBy("Age", false, "LastName", true, "FirstName", false); 
//Will return John Foo/John Doe/Jane Doe 
2
grouperArray.sort((a, b) => a.gsize - b.gsize || a.glow - b.glow); 

Incluso versión más corta usando la sintaxis de la flecha!

Cuestiones relacionadas