在javascript中搜索对象数组中的深层嵌套值

时间:2017-08-21 12:17:53

标签: javascript arrays

我基本上试图实现对任何给定值的搜索,应该查看对象键值数组(也可以有嵌套对象)。这是一个例子。下面的函数将使用一个对象和一个查询来搜索数组对象的键值。因此,如果找到匹配项,则应从该数组中过滤。

function searchObj (obj, query) {
  for (var key in obj) {
    var value = obj[key];
    if (typeof value === 'object') {
       searchObj(value, query);
    }
    if (typeof value === 'string' && value.toLowerCase().indexOf(query.toLowerCase()) > -1) {
       return obj;
    }
  }
}

这里是虚拟数据

var demoData=[
  {id:1,desc:{original:'trans1'},date:'2017-07-16'},
  {id:2,desc:{original:'trans2'},date:'2017-07-12'},
  {id:3,desc:{original:'trans3'},date:'2017-07-11'},
  {id:4,desc:{original:'trans4'},date:'2017-07-15'}
];

这里是数组I' m匹配的过滤对象

var searchFilter = demoData.filter(function(obj){
     return searchObj(obj, 'trans1');
});
console.log(searchFilter);

例如:如果我调用searchObj(obj,'2017-07-15')它会返回该特定对象,但如果我搜索trans1或只是trans,它应该查看该对象然后返回匹配。我现在有点被困,任何帮助都会受到赞赏。感谢。

2 个答案:

答案 0 :(得分:3)

案例1正在运行,因为您没有进行递归。但是在第2种情况下,即使找到了结果,你也会继续搜索。

找到后返回对象。

if (typeof value === 'object') {
       return searchObj(value, query);
    }
    if (typeof value === 'string' && value.toLowerCase().indexOf(query.toLowerCase()) > -1) {
       return obj;
    }



function searchObj (obj, query) {

  for (var key in obj) {
    var value = obj[key];
    if (typeof value === 'object') {
       return searchObj(value, query);
    }
    if (typeof value === 'string' && value.toLowerCase().indexOf(query.toLowerCase()) > -1) {
       return obj;
    }
  }
}

var demoData=[
  {id:1,desc:{original:'trans1'},date:'2017-07-16'},
  {id:2,desc:{original:'trans2'},date:'2017-07-12'},
  {id:3,desc:{original:'trans3'},date:'2017-07-11'},
  {id:4,desc:{original:'trans4'},date:'2017-07-15'}
];

var searchFilter = demoData.filter(function(obj){
     return searchObj(obj, 'trans1');
});
console.log(searchFilter);




答案 1 :(得分:0)

查看此问题的另一种方法是只使用JSON.stringify并在其中搜索:

searchObj(obj, string) {
  const regExpFlags = 'gi',
        regExp = new RegExp(string, regExpFlags);
  return JSON.stringify(obj).match(regExp);
}

然后测试搜索模式:

var searchFilter = demoData.filter(function(obj){
 return searchObj(obj, 'trans1');
});
console.log(searchFilter);

您甚至可以通过提供字符串数组来进一步进行松散搜索:

searchObj(obj, string) {
 const jsonString = JSON.stringify(obj);
       regExpFlags = 'gi',
       regExpArray = string.split(' ');
       testArray = [];

 regExpArray.forEach(term => {
   let regExp = new RegExp(term, regExpFlags);
   if (jsonString.match(regExp) {
     testArray.push(term);
   }
 });

 return regExpArray.length === testArray.length;
}

我修改了数据:

var demoData=[
  {id:1,desc:{original:'trans1'},date:'2017-07-16'},
  {id:1,desc:{original:'trans2'},date:'2017-07-12'},
  {id:1,desc:{original:'trans3'},date:'2017-07-13'},
  {id:2,desc:{original:'trans4'},date:'2017-07-12'},
  {id:3,desc:{original:'trans5'},date:'2017-07-12'},
  {id:4,desc:{original:'trans6'},date:'2017-07-15'},
  {id:1,desc:{original:'trans7'},date:'2017-07-12'}
];

搜索词:

var searchFilter = demoData.filter(function(obj){
 return searchObj(obj, 'trans 2017-07-12');
});
console.log(searchFilter);

这里要注意的重要一件事是JSON.stringify的性能,因此在深度嵌套对象数量有限(<1000)的情况下,这对我来说效果很好。

可能会有更多经验的人对此有所了解。