在JavaScript

时间:2018-04-26 20:23:28

标签: javascript jquery arrays ajax object

我有一个名为Filter的对象,它存储有关Car Types的信息。通过AJAX检索此信息,并在第一个ajax调用对象0-10创建并推送到数组。在第二个ajax调用中,返回更多的汽车类型并添加到阵列中。

我的问题是:我只想用具有唯一标签的数组添加对象。因此,对于下一个AJAX调用,我只想将标签为“Hybrid”的对象添加到数组中。这就是我所拥有的,由于某种原因,indexOf方法似乎不起作用,并且正在向阵列中添加具有相同标签的所有新车类型。

代码:

var filter_object = Object.create(Filter);
filter_object.init(label, $(this).val());


if (types.indexOf(filter_object.label) == -1)
   types.push(filter_object);


  var Filter = {
     init: function (label, value) {
        this.label = label;
        this.value = value;
     }
  };

示例对象:

0:   {label: "All Car Types", value: "on"}
1:   {label: "Small Cars", value: "CCAR,ECAR,CDAR,EDAR"}
2:   {label: "Medium Cars", value: "ICAR,SCAR,IDAR"}
3:   {label: "Large Cars", value: "FCAR,PCAR,FDAR"}
4:   {label: "SUVs & Crossovers", value: "IFAR,SFAR,CFAR,RFAR,FFAR,PFAR"}
5:   {label: "Vans", value: "MVAR,RVAR,FVAR"}
6:   {label: "Luxury", value: "LCAR,LDAR"}
7:   {label: "Convertibles", value: "STAR"}
8:   {label: "Sports", value: "SSAR"}
9:   {label: "Commercial", value: "SKAR"}
10:  {label: "Specialty", value: "XXAR"}


// Next AJAX Call
11: {label: "All Car Types", value: "on"}
12: {label: "Small Cars", value: "ECAR,MCAR,CCAR,CDAR,EDAR"}
13: {label: "Hybrids", value: "ICAH,FCAH"}

3 个答案:

答案 0 :(得分:1)

我之前的尝试错过了必须合并价值的要求。我仍然不确定你的数据结构,但如果这些可以是在数组中收集的简单对象,那么这可能会:

const combineValues = (v1, v2) => {
  const a1 = v1.split(','), a2 = v2.split(',');
  return a1.concat(a2.filter(v => !(a1.includes(v)))).join(',')
}
// combineValues('a,b,c,d', 'a,b,c,e,f') //=> "a,b,c,d,e,f"

const combineTypes = (types, newTypes) => {
  return types.map(type => {
    const matchType = newTypes.find(t => t.label === type.label) || type
    return {label: type.label, value: combineValues(type.value, matchType.value)}
  }).concat(newTypes.filter(type => types.every(t => t.label !== type.label)))
}


const types = [{"label": "All Car Types", "value": "on"}, {"label": "Small Cars", "value": "CCAR,ECAR,CDAR,EDAR"}, {"label": "Medium Cars", "value": "ICAR,SCAR,IDAR"}, {"label": "Large Cars", "value": "FCAR,PCAR,FDAR"}, {"label": "SUVs & Crossovers", "value": "IFAR,SFAR,CFAR,RFAR,FFAR,PFAR"}, {"label": "Vans", "value": "MVAR,RVAR,FVAR"}, {"label": "Luxury", "value": "LCAR,LDAR"}, {"label": "Convertibles", "value": "STAR"}, {"label": "Sports", "value": "SSAR"}, {"label": "Commercial", "value": "SKAR"}, {"label": "Specialty", "value": "XXAR"}]
const newTypes = [{"label": "All Car Types", "value": "on"}, {"label": "Small Cars", "value": "ECAR,MCAR,CCAR,CDAR,EDAR"}, {"label": "Hybrids", "value": "ICAH,FCAH"}]


const updated = combineTypes(types, newTypes)
console.log(updated)

请注意,这会结合“小型车”中的值并添加“混合动力车”。它不会改变您的任何数据,而是创建一个包含新对象的新数组。

代码简单性包含一些愚蠢的低效率。如果找不到匹配的新类型,我们会在类型和本身上调用combineValues,显然无用。虽然解决这个问题并不困难,但代码会更加丑陋。考虑到可能的元素数量,我无法想象这会有问题。

答案 1 :(得分:0)

你应该使用es6的.some,如

if (!types.some(e=> e.label === filter_object.label))
 types.push(filter_object);

注意:some()方法测试数组中是否至少有一个元素通过了由提供的函数实现的测试。 Here

答案 2 :(得分:0)

您可以创建一个包含所有现有标签的新数组作为查找,然后在传入的数组上调用.reduce,如下所示:

const existingLabels = existing.map(item => item.label);

const updated = newItems.reduce((all, item) => {
  if (!existingLabels.includes(item.label))
      all.push(item);

  return all;
}, existing);