【问题标题】:javascript - return parent with only child that matches given search string in array of objects with nested objectjavascript - 返回具有唯一子级的父级,该子级与具有嵌套对象的对象数组中的给定搜索字符串匹配
【发布时间】:2017-11-18 04:59:39
【问题描述】:

这是来自my previous question 的后续问题。根据我收到的答案,我可以在对象数组中的嵌套对象中进行搜索。

请找到这个fiddle for example

var data = [
{
  'booking_name': 'gtec/1101822/lmikdy/ls-rmea/oss11',
  'asset_count': 2,
  'pdg': 'Invalid',
  'user_area': 'Invalid',
  'deployment_number': 'Invalid',
  'spoc': 'invalid',
  'release': 'Invalid',
  'start_date': '2017-06-12 00:00:00',
  'end_date': '2017-06-16 00:00:00',
  'asset_info': [
    {
      'bams_id': 'BAMS-1001423507',
      'hostname': 'GTVOSS11',
      'status': 10,
      'site_location': 'IEAT01 Tipperary',
      'rack_number': 'VIRTUAL RACK',
      'rack_u_position': 0,
      'manufacturer': 'EMC',
      'model': 'VM',
      
    },
    {
      'bams_id': 'BAMS-1001368001',
      'hostname': 'None',
      'status': 10,
      'site_location': 'IEAT01 Tipperary',
      'rack_number': 'VIRTUAL RACK',
      'rack_u_position': 0,
      'manufacturer': 'HP',
      'model': 'HP BL460C GEN8',
      
    }
],
'full_name': 'Invalid (invalid)',
'email_address': 'Invalid'
},
{
  'booking_name': 'gtec/1101822/lmikdy/ls-rmea/oss11',
  'asset_count': 2,
  'pdg': 'Invalid',
  'user_area': 'Invalid',
  'deployment_number': 'Invalid',
  'spoc': 'invalid',
  'release': 'Invalid',
  'start_date': '2017-06-12 00:00:00',
  'end_date': '2017-06-16 00:00:00',
  'asset_info': [
    {
      'bams_id': 'BAMS-1001423507',
      'hostname': 'GTVOSS11',
      'status': 10,
      'site_location': 'IEAT01 Tipperary',
      'rack_number': 'VIRTUAL RACK',
      'rack_u_position': 0,
      'manufacturer': 'EMC',
      'model': 'VM',
      
    }
],
'full_name': 'Invalid (invalid)',
'email_address': 'Invalid'
}];

在这里,当我搜索字符串“emc”时,该函数返回两个正确的对象。但是作为“制造商”的“emc”在子对象中。并且每个子对象都不满足这个条件。我正在寻找的结果,例如“emc”,它应该返回 2 个父对象。第一个父对象应该只有一个孩子(另一个孩子有'hp'作为制造商)。第二个父对象应该有一个子对象,因为它与搜索字符串匹配。

我尝试使用搜索结果创建一个新对象,但无法正常工作。

如何返回满足给定搜索字符串的唯一子对象的父对象?

这里是chatlog on my previous question,可以帮助您了解问题和要求。

【问题讨论】:

  • 如果这样做,您将不再拥有相同的父对象,因为它的子对象已更改。您可以为两个父对象添加一个唯一标识符,并根据该唯一身份返回一组匹配结果?
  • @Icepickle 没关系,如果我没有相同的父母。但对象格式(键)应该相同。最后我会返回新的搜索到的数据来绑定到表中。

标签: javascript arrays


【解决方案1】:

您可以使用迭代和递归方法,如果子项与搜索值匹配,则返回检查结果并构建新对象和数组。

function getValue(item) {
    if (Array.isArray(item)) {
        return item.reduce(iterA, undefined);
    }
    if (item && typeof item === 'object') {
        return iterO(item);
    }
    if (typeof item !== 'object' && item.toString().toLowerCase().indexOf(search) !== -1) {
        return item;
    }
}

function iterO(o) {
    var temp = Object.keys(o).reduce(function (r, k) {
            var value = getValue(o[k]);
            if (value) {
                r = r || {};
                r[k] = value;
            }
            return r;
        }, undefined);

    if (temp) {
        Object.keys(o).forEach(function (k) {
            if (!(k in temp)) {
                temp[k] = o[k];
            }
        });
    }
    return temp;
}

function iterA(r, a) {
    var value = getValue(a);
    if (value) {
        r = r || [];
        r.push(value);
    }
    return r;
}

var data = [{ booking_name: "gtec/1101822/lmikdy/ls-rmea/oss11", asset_count: 2, pdg: "Invalid", user_area: "Invalid", deployment_number: "Invalid", spoc: "invalid", release: "Invalid", start_date: "2017-06-12 00:00:00", end_date: "2017-06-16 00:00:00", asset_info: [{ bams_id: "BAMS-1001423507", hostname: "GTVOSS11", status: 10, site_location: "IEAT01 Tipperary", rack_number: "VIRTUAL RACK", rack_u_position: 0, manufacturer: "EMC", model: "VM" }, { bams_id: "BAMS-1001368001", hostname: "None", status: 10, site_location: "IEAT01 Tipperary", rack_number: "VIRTUAL RACK", rack_u_position: 0, manufacturer: "HP", model: "HP BL460C GEN8" }], full_name: "Invalid (invalid)", email_address: "Invalid" }, { booking_name: "gtec/1101822/lmikdy/ls-rmea/oss11", asset_count: 2, pdg: "Invalid", user_area: "Invalid", deployment_number: "Invalid", spoc: "invalid", release: "Invalid", start_date: "2017-06-12 00:00:00", end_date: "2017-06-16 00:00:00", asset_info: [{ bams_id: "BAMS-1001423507", hostname: "GTVOSS11", status: 10, site_location: "IEAT01 Tipperary", rack_number: "VIRTUAL RACK", rack_u_position: 0, manufacturer: "EMC", model: "VM" }], full_name: "Invalid (invalid)", email_address: "Invalid" }],
    search = 'emc',
    result = data.reduce(iterA, undefined);

console.log(result);
.as-console-wrapper { max-height: 100% !important; top: 0; }

【讨论】:

  • 为什么不使用Object.assign 来复制值?
  • 好吧,但是reduce 也是 es6,不是吗? (不是我想打扰你,热爱你的工作;))
  • @Icepickle,reduce 是 ES5,afaik。
  • @NinaScholz 完美解决方案。效果很好。非常感谢。
  • @Icepickle es6 目前超出了我的范围。感谢 es6 的解决方案。
【解决方案2】:

我不确定你的方法需要走多远,但这应该可以解决问题

当子项有每一行时,它会复制每一行,并只用匹配的值替换集合

function filterSet(dataSet, matchFn) {
  return dataSet.reduce((current, row) => {
    if (typeof row === 'object') {
      for (let prop in row) {
        if (Array.isArray(row[prop])) {
          var set = filterSet(row[prop], matchFn);
          if (set && set.length > 0) {
            // copy the row, replace the array property with the results
            current.push( Object.assign({}, row,
              { [prop]: set }
            ) );
            // since the full row is now in there
            // no need to check more
            break;
          }
        } else if (matchFn(row[prop])) {
            // copy not ref
            current.push( Object.assign( {}, row ) );
            break;
          }
      }
    }
    return current;
  }, []);
}

var data = [{
    'booking_name': 'gtec/1101822/lmikdy/ls-rmea/oss11',
    'asset_count': 2,
    'pdg': 'Invalid',
    'user_area': 'Invalid',
    'deployment_number': 'Invalid',
    'spoc': 'invalid',
    'release': 'Invalid',
    'start_date': '2017-06-12 00:00:00',
    'end_date': '2017-06-16 00:00:00',
    'asset_info': [{
        'bams_id': 'BAMS-1001423507',
        'hostname': 'GTVOSS11',
        'status': 10,
        'site_location': 'IEAT01 Tipperary',
        'rack_number': 'VIRTUAL RACK',
        'rack_u_position': 0,
        'manufacturer': 'EMC',
        'model': 'VM',

      },
      {
        'bams_id': 'BAMS-1001368001',
        'hostname': 'None',
        'status': 10,
        'site_location': 'IEAT01 Tipperary',
        'rack_number': 'VIRTUAL RACK',
        'rack_u_position': 0,
        'manufacturer': 'HP',
        'model': 'HP BL460C GEN8',

      }
    ],
    'full_name': 'Invalid (invalid)',
    'email_address': 'Invalid'
  },
  {
    'booking_name': 'gtec/1101822/lmikdy/ls-rmea/oss11',
    'asset_count': 2,
    'pdg': 'Invalid',
    'user_area': 'Invalid',
    'deployment_number': 'Invalid',
    'spoc': 'invalid',
    'release': 'Invalid',
    'start_date': '2017-06-12 00:00:00',
    'end_date': '2017-06-16 00:00:00',
    'asset_info': [{
      'bams_id': 'BAMS-1001423507',
      'hostname': 'GTVOSS11',
      'status': 10,
      'site_location': 'IEAT01 Tipperary',
      'rack_number': 'VIRTUAL RACK',
      'rack_u_position': 0,
      'manufacturer': 'EMC',
      'model': 'VM',

    }],
    'full_name': 'Invalid (invalid)',
    'email_address': 'Invalid'
  }
];

console.log(filterSet(data, (i) => {
  return i.toString().toLowerCase().indexOf('emc') >= 0;
}));

console.log(filterSet(data, (i) => {
  return i.toString().toLowerCase().indexOf('invalid') >= 0;
}));

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2020-08-27
    • 1970-01-01
    • 2012-06-06
    • 2021-09-25
    • 2019-10-25
    • 1970-01-01
    • 2021-01-19
    • 1970-01-01
    相关资源
    最近更新 更多