簡體   English   中英

按鍵值對過濾數組中的對象

[英]Filter objects in array by key-value pairs

我有一個像這樣的對象數組:

    [
      {
        id: 'a',
        name: 'Alan',
        age: 10
      },
      {
        id: 'ab'
        name: 'alanis',
        age: 15
      },
      {
        id: 'b',
        name: 'Alex',
        age: 13
      }
    ]

我需要傳遞一個類似{ id: 'a', name: 'al' }以便它執行通配符過濾並返回包含前兩個對象的數組。

因此,步驟如下:

  1. 對於數組中的每個對象,從給定的過濾器對象中過濾相關的鍵

  2. 對於每個鍵,請檢查值是否以匹配的過濾器對象鍵的值開頭

目前,我正在使用lodash的過濾器功能,以便它執行完全匹配,而不是以/通配符類型開頭的匹配。 這就是我在做什么:

filter(arrayOfObjects, filterObject)

如果我正確理解了您的問題, startsWith是您要尋找的關鍵術語嗎?

 const arr = [ { id: 'a', name: 'Alan', age: 10 }, { id: 'ab', name: 'alanis', age: 15 }, { id: 'b', name: 'Alex', age: 13 } ]; const searchTerm = { id: 'a', name: 'al' } const result = arr.filter(x => x.id === searchTerm.id || x.name.startsWith(searchTerm.name) ); console.log(result) 

認為您正在尋找這樣的東西? 基本上將做一個string.includes匹配過濾器對象中每個鍵的值-如果其中一個鍵值匹配,則它將包含在結果中。 如果您希望整個過濾器對象匹配,則可以執行.every而不是.some ...

const data = [
  {
    id: 'a',
    name: 'Alan',
    age: 10
  },
  {
    id: 'ab',
    name: 'alanis',
    age: 15
  },
  {
    id: 'b',
    name: 'Alex',
    age: 13
  }
]

const filter = { id: 'a', name: 'al' }

function filterByObject(filterObject, data) {
  const matched = data.filter(object => {
    return Object.entries(filterObject).some(([filterKey, filterValue]) => {
      return object[filterKey].includes(filterValue)
    })
  })
  return matched
}

console.log(filterByObject(filter, data))

您可以創建一個自定義方法,該方法使用成對的(key, regular expression)Object.entries()上的Array.filter()迭代器來接收和對象,以檢查是否匹配。

 let input = [ {id: 'a', name: 'Alan', age: 10}, {id: 'ab', name: 'alanis', age: 15}, {id: 'b', name: 'Alex', age: 13} ]; const filterWithSome = (arr, obj) => { return arr.filter(o => { return Object.entries(obj).some(([k, v]) => o[k].match(v)); }); } console.log(filterWithSome(input, {id: /^a/, name: /^al/})); 
 .as-console {background-color:black !important; color:lime;} .as-console-wrapper {max-height:100% !important; top:0;} 

相反,如果您希望匹配作為參數傳遞的對象的每個(key, regular expression) ,則可以將Array.some()替換為Array.every()

 let input = [ {id: 'a', name: 'Alan', age: 10}, {id: 'ab', name: 'alanis', age: 15}, {id: 'b', name: 'Alex', age: 13} ]; const filterWithEvery = (arr, obj) => { return arr.filter(o => { return Object.entries(obj).every(([k, v]) => o[k].match(v)); }); } console.log(filterWithEvery(input, {id: /^ab/, name: /^al/})); 
 .as-console {background-color:black !important; color:lime;} .as-console-wrapper {max-height:100% !important; top:0;} 

用於動態對象過濾器。 您可以closurereduce

 const data = [ {id: 'a',name: 'Alan',age: 10}, {id: 'ab',name: 'alanis',age: 15}, {id: 'b',name: 'Alex',age: 13} ] const queryObj = { id: 'a', name: 'al' } const queryObj2 = { name: 'al', age: 13 } const filterWith = obj => e => { return Object.entries(obj).reduce((acc, [key, val]) => { if(typeof val === 'string') return acc || e[key].startsWith(val) else return acc || e[key] === val }, false) } const filter1 = filterWith(queryObj) const filter2 = filterWith(queryObj2) console.log(data.filter(filter1)) console.log(data.filter(filter2)) 

暫無
暫無

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

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