如何对 JavaScript 中的对象集合进行自然排序?

How to natural-sort a collection of objects in JavaScript?

Belong 是我的对象集合的一个示例。

const a = [
    {name: "John", size: "100"},
    {name: "John", size: "80"},
    {name: "John", size: "82"},
    {name: "John", size: "110"},
    {name: "John", size: "70"},
    {name: "John", size: "M"},
    {name: "John", size: "S"},
    {name: "John", size: "XS"},
    {name: "John", size: "L"},
    {name: "John", size: "XL"},
]

以100大于80,100排在80之后为例,JavaScript如何自然排序?

挑战在于 size 的值是数字和字符串的混合。

期望的升序结果:

[
    {name: "John", size: "70"},
    {name: "John", size: "80"},
    {name: "John", size: "82"},
    {name: "John", size: "100"},
    {name: "John", size: "110"},
    {name: "John", size: "L"},
    {name: "John", size: "M"},
    {name: "John", size: "S"},
    {name: "John", size: "XL"},
    {name: "John", size: "XS"},
]

降序所需结果:

[
    {name: "John", size: "XS"},
    {name: "John", size: "XL"},
    {name: "John", size: "S"},
    {name: "John", size: "M"},
    {name: "John", size: "L"},
    {name: "John", size: "110"},
    {name: "John", size: "100"},
    {name: "John", size: "82"},
    {name: "John", size: "80"},
    {name: "John", size: "70"},
]

我已经按升序尝试了 Lodash JavaScript 库,但它没有正确排序,因为它看到 100 小于 80 因为 1001

_.orderBy(a, ["size"], ["asc"])

您可以使用正常的 JavaScript 逻辑来实现。您可以显式创建一个尺寸映射,这将帮助您根据要求对值进行排序:

const a = [
    {name: "John", size: "100"},
    {name: "John", size: "80"},
    {name: "John", size: "82"},
    {name: "John", size: "110"},
    {name: "John", size: "70"},
    {name: "John", size: "M"},
    {name: "John", size: "S"},
    {name: "John", size: "XS"},
    {name: "John", size: "L"},
    {name: "John", size: "XL"},
];
var sizes = {
  '100': 3,
  '80': 1,
  '82': 2,
  '110': 4,
  '70': 0,
  'M': 6,
  'S': 7,
  'XS': 9,
  'L': 5,
  'XL': 8,
}
//ascending
a.sort((x, y) => {
  return sizes[x.size] - sizes[y.size];
});

console.log(a);

//descending
a.sort((x, y) => {
  return sizes[y.size] - sizes[x.size];
});

console.log(a);

  let array_data = [
    {name: "John", size: "70"},
    {name: "John", size: "80"},
    {name: "John", size: "82"},
    {name: "John", size: "100"},
    {name: "John", size: "110"},
    {name: "John", size: "L"},
    {name: "John", size: "M"},
    {name: "John", size: "S"},
    {name: "John", size: "XL"},
    {name: "John", size: "XS"},
];

    let  sorted = array_data.sort((a, b) => {return parseInt(a.size) - parseInt(b.size);});
    console.log(sorted);

正常排序 javascript 功能将起作用。

Ascending and Descending order

const arr = [{name: "John", size: "100"},{name: "John", size: "80"},{name: "John", size: "82"},{name: "John", size: "110"},{name: "John", size: "70"},{name: "John", size: "M"},{name: "John", size: "S"},{name: "John", size: "XS"},{name: "John", size: "L"},{name: "John", size: "XL"}],
      handler = (a, b, desc) => {
        if (isNaN(+a) && isNaN(+b)) return (desc ? b.localeCompare(a) : a.localeCompare(b));
        else if (!isNaN(+a) && !isNaN(+b)) return (desc ? (+b - +a) : (+a - +b));
        else if (isNaN(+a)) return (desc ? -1 : 1); 
        else return (desc ? 1 : -1);
      },
      descending = arr.sort(({size: a}, {size: b}) => handler(a, b, true)),
      ascending = [...arr].sort(({size: a}, {size: b}) => handler(a, b));

console.log("Ascending")
console.log(ascending);
console.log("Descending")
console.log(descending);
.as-console-wrapper { max-height: 100% !important; top: 0; }

因为您已经在使用 loadsh。只需编写一个函数来评估 size 是 String 还是 Integer,然后它将为您排序。

对于desc,只需将asc数组反转即可。

const a = [ {name: "John", size: "100"}, {name: "John", size: "80"}, {name: "John", size: "82"}, {name: "John", size: "110"}, {name: "John", size: "70"}, {name: "John", size: "M"},    {name: "John", size: "S"}, {name: "John", size: "XS"}, {name: "John", size: "L"}, {name: "John", size: "XL"} ];

// ascednding
const b = _.orderBy(a, function(e) { return isNaN(e.size) ? e.size: parseInt(e.size)}, ["asc"]);
console.log("ASCENDING::");
console.log(b);

//descending
const c = _.reverse(b);
console.log("DESCENDING::");
console.log(c);
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.11/lodash.min.js"></script>

const a = [
  {name: "John", size: "100"},
  {name: "John", size: "80"},
  {name: "John", size: "82"},
  {name: "John", size: "110"},
  {name: "John", size: "70"},
  {name: "John", size: "M"},
  {name: "John", size: "S"},
  {name: "John", size: "XS"},
  {name: "John", size: "L"},
  {name: "John", size: "XL"},
 ]
// ascending
const sorted = arr => [...arr].sort((a, b) => a.size.localeCompare(b.size, 'en', {numeric: true}))
console.log(sorted(a))