簡體   English   中英

如何使用ramda按數組對象中的最后一項排序

[英]How to use ramda to sort by last item in an array object

以下是父母名單,我想按拉姆達分類按其第二個孩子的年齡進行排序:

[
  {
    name: "Alicia",
    age: "43",
    children: [{
        name: "Billy",
        age: "3"
      },
      {
        name: "Mary",
        age: "8"
      },
    ]
  },
  {
    name: "Felicia",
    age: "60",
    children: [{
        name: "Adrian",
        age: "4"
      },
      {
        name: "Joseph",
        age: "5"
      },
    ]
  }
]

我該如何處理? 我嘗試按照以下方式做一些事情

parents.sort(
                sortBy("-children.age"))
            );

使用R.sortBy並提取與函數與創造的價值R.pipe 該函數使用R.prop獲取對象的children數組,獲取最后一個孩子( R.last ),使用R.propOr獲取age (如果沒有孩子則返回0),然后轉換為Number 如果要R.negate順序,可以使用R.negate

 const { sortBy, pipe, prop, last, propOr } = R const fn = sortBy(pipe( prop('children'), last, propOr(0, 'age'), Number, // negate - if you want to reverse the order )) const parents = [{"name":"Alicia","age":"43","children":[{"name":"Billy","age":"3"},{"name":"Mary","age":"8"}]},{"name":"Felicia","age":"60","children":[{"name":"Adrian","age":"4"},{"name":"Joseph","age":"5"}]}] const result = fn(parents) console.log(result) 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/ramda/0.26.1/ramda.js"></script> 

在原始JavaScript中(使用一些相對格式較差的假設),使用Array.prototype.sort方法:

let parents = [ .... ]; // What you have above
parents = parents.sort((a, b) => {
  return a.children[1].age - b.children[1].age; // Change - to + for ascending / descending
});

不過要小心-如果父母少於兩個孩子會怎樣?

假設上面的JSON是手工生成的,包括語法錯誤,然后假設您的真實數據很好(一個父級數組,每個父級都有一個對象的children級數組),那么普通的JS排序就可以了:

const compareC2(parent1, parent2) {
  let c1 = parent1.children;
  let c2 = parent2.children;

  if (!c1 || !c2) {
    // what happens if someone has no children?
  }

  let l1 = c1.length;
  let l2 = c2.length;

  if (l1 === 0 || l2 === 0) {
    // different symptom, but same question as above
  }

  if (l1 !== l2) {
    // what happens when the child counts differ?
  }

  if (l1 !== 2) {
    // what happens when there are fewer, or more than, 2 children?
  }

  // after a WHOLE LOT of assumptions, sort based on
  // the ages of the 2nd child for each parent.
  return c1[1].age - c2[1].age;
}  

let sorted = parents.sort(compareC2);

我會用sortWithascend的功能。 使用sortWith允許您定義第一個排序順序函數,第二個排序順序函數等。

 const people = [ { name: "Alicia", age: "43", children: [{ name: "Billy", age: "3" }, { name: "Mary", age: "8" }, ] }, { name: "Felicia", age: "60", children: [{ name: "Adrian", age: "4" }, { name: "Joseph", age: "5" }, ] } ]; const by2ndChildAge = ascend(pathOr(0, ['children', 1, 'age'])); const by1stChildAge = ascend(pathOr(0, ['children', 0, 'age'])); console.log(sortWith([by2ndChildAge, by1stChildAge], people)); 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/ramda/0.26.1/ramda.min.js"></script> <script>const {sortWith, ascend, pathOr} = R;</script> 

我認為,最簡單的解決方案是將sortBypath結合使用:

 const sortBy2ndChildAge = sortBy(path(['children', 1, 'age'])) const people = [{name: "Alicia", age: "43", children: [{name: "Billy", age: "3"}, {name: "Mary", age: "8"}]}, {name: "Felicia", age: "60", children: [{name: "Adrian", age: "4"}, {name: "Joseph", age: "5"}]}] console.log(sortBy2ndChildAge(people)) 
 <script src="https://bundle.run/ramda@0.26.1"></script><script> const {sortBy, path} = ramda </script> 

其他人已經指出,這樣做存在一些潛在的缺陷。 父母是否總是保證至少有兩個孩子? 我們是否真的要按字典順序排序-即'11' < '2' 2'-還是要將這些值轉換為數字?

解決這兩個問題很容易: sortBy(compose(Number, pathOr(0, ['children', 1, 'age']))) ,但這取決於您要執行的操作。 如果您只是用來學習sortBy ,那么sortBypath都是有用的函數。 當您可以將要排序的項目轉換為某種有序類型時, sortBy很有用-字符串,數字,日期或帶有數值valueOf方法的任何內容。 您提供該轉換函數和值列表,它將按此排序。 path只是對對象中的嵌套屬性列表的null安全讀取。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM