如何比较JSON格式的数组VALUE和KEY来创建新的数组?在Angular 5中


10

这是我的第一个JSON数组格式:

this.columnNames = [
  {field : "Name"},
  {field : "Address"},
  {field : "Age"}
];

这是我的第一个JSON数组格式:

this.rowData = [
  {Name : "Praveen",Address : "aiff",Age : "12",w :  "1",e :  "8"},
  {Name : "Akashay",Address : "xvn",Age : "15",w :  "2",e :  "7"},
  {Name : "Bala",Address : "hjk",Age : "16",w :  "3",e :  "6"}, 
  {Name : "Charu",Address : "sss",Age : "17",w :  "4",e :  "5"},
];  

在这里,我想比较第一个array(columnNames)数组中存在的VALUE 和第二个数组中存在的KEYS。如果相等,那么我想将第二个匹配的数据推array(rowData)送到新数组中。

我想要这样的最终结果:

public rowData: any =[
  {Name : "Praveen",Address : "aiff",Age : "12"},
  {Name : "Akashay",Address : "xvn",Age : "15"},
  {Name : "Bala",Address : "hjk",Age : "16"}, 
  {Name : "Charu",Address : "sss",Age : "17"},
];

您自己尝试过吗?
TylerH

Answers:


10

使用捕获columnNames数组中每个对象的字段.map()。然后,将每个对象映射rowData到使用创建的新对象.reduce(),该对象仅包含fields数组中的键:

const columnNames = [
  {field : "Name"},
  {field : "Address"},
  {field : "Age"}
];

const rowData = [
  {Name : "Praveen",Address : "aiff",Age : "12",w :  "1",e :  "8"},
  {Name : "Akashay",Address : "xvn",Age : "15",w :  "2",e :  "7"},
  {Name : "Bala",Address : "hjk",Age : "16",w :  "3",e :  "6"}, 
  {Name : "Charu",Address : "sss",Age : "17",w :  "4",e :  "5"},
];  

const fields = columnNames.map(({field}) => field); // get array ["Name", "Address", "Age"]
const result = rowData.map( // map each object in rowData to a new object
  o => fields.reduce((obj, k) => ({...obj, [k]: o[k]}), {})
  //    ^^ construct the new object, using reduce, spread syntax and computed property names
);

console.log(result);
.as-console-wrapper { max-height: 100% !important;} /* ignore */

如果可以支持Object.fromEntries()(它需要一个嵌套[key, value]对数组,并从它们中构建一个对象),则无需使用.reduce()

const columnNames = [
  {field : "Name"},
  {field : "Address"},
  {field : "Age"}
];

const rowData = [
  {Name : "Praveen",Address : "aiff",Age : "12",w :  "1",e :  "8"},
  {Name : "Akashay",Address : "xvn",Age : "15",w :  "2",e :  "7"},
  {Name : "Bala",Address : "hjk",Age : "16",w :  "3",e :  "6"}, 
  {Name : "Charu",Address : "sss",Age : "17",w :  "4",e :  "5"},
];  

const fields = columnNames.map(({field}) => field);
const result = rowData.map( 
  o => Object.fromEntries(fields.map(k => [k, o[k]]))
);

console.log(result);
.as-console-wrapper { max-height: 100% !important;} /* ignore */


嗨,我有问题。你能解决我的问题吗?:)这里是链接[ stackoverflow.com/questions/60089217/...
Sakkeer一个

5

您可以filter基于columnNames数组来设置对象属性,然后使用Object.fromEntries以下命令创建一个对象:

const result = rowData.map(s => Object.fromEntries(
    Object.entries(s).filter(([k, v]) => columnNames.some(cl => cl.field == k))));

一个例子:

let columnNames = [
  {field : "Name"},
  {field : "Address"},
  {field : "Age"}
];

let rowData = [
  {Name : "Praveen",Address : "aiff",Age : "12",w :  "1",e :  "8"},
  {Name : "Akashay",Address : "xvn",Age : "15",w :  "2",e :  "7"},
  {Name : "Bala",Address : "hjk",Age : "16",w :  "3",e :  "6"},
  {Name : "Charu",Address : "sss",Age : "17",w :  "4",e :  "5"},
];

const result = rowData.map(s => Object.fromEntries(
    Object.entries(s).filter(([k, v]) => columnNames.some(cl => cl.field == k))));
console.log(result);

或更可调试的版本:

const result = rowData.map(s => {
  let allProperties = Object.entries(s);
  let filteredProperties = allProperties.filter(([k, v]) => 
      columnNames.some(cl => cl.field == k));
  let result = Object.fromEntries(filteredProperties);
  return result;
})

一个例子:

let columnNames = [
  {field : "Name"},
  {field : "Address"},
  {field : "Age"}
];

let rowData = [
  {Name : "Praveen",Address : "aiff",Age : "12",w :  "1",e :  "8"},
  {Name : "Akashay",Address : "xvn",Age : "15",w :  "2",e :  "7"},
  {Name : "Bala",Address : "hjk",Age : "16",w :  "3",e :  "6"},
  {Name : "Charu",Address : "sss",Age : "17",w :  "4",e :  "5"},
];

const result = rowData.map(s => {
  let allProperties = Object.entries(s);
  let filteredProperties = allProperties.filter(([k, v]) => 
      columnNames.some(cl => cl.field == k));
  let result = Object.fromEntries(filteredProperties);
  return result;
})

Object.fromEntries是将键值对列表转换为对象的方法。

下一行表示我们基于array 过滤() 数组。allProperiescolumnNames

true如果中columnNames存在的某些属性,则some()方法返回allProperties

let filteredProperties = allProperties.filter(([k, v]) => 
     columnNames.some(cl => cl.field == k)); 

非常感谢您的回复。我对此表示怀疑,我是8号角的初学者,我不知道什么是“ Object.fromEntries”,还可以请您解释一下这一点吗? => columnNames.some(cl => cl.field == k));“。感谢您的大力支持!
Praveen Sivanadiyar

@PraveenSivanadiyar,请参阅我的最新答案
StepUp

@StepUp嗨,我有问题。你能解决我的问题吗?:)这里是链接[ stackoverflow.com/questions/60089217/...
Sakkeer一个

3

keys使用.map将所有字段名称存储在变量中。然后遍历原始数组并创建一个具有以下属性的对象:keys

尝试这样:

let keys = this.columnNames.map(x => x.field);

this.rowData.forEach(item => {
  let obj = {}
  keys.forEach(key => {
    obj[key] = item[key]
  });
  this.result.push(obj)
});

工作演示


你能解释一下这里会发生什么吗?keys.forEach(key => {obj [key] = item [key]});
Praveen Sivanadiyar

当然,我要添加说明
Adrita Sharma

@PraveenSivanadiyar添加了描述。让我知道这是否有帮助
Adrita Sharma

1
obj是一个新的空对象。obj[key] = item[key] 意思是,在第一个循环中,键是“名称”,所以obj[key]将是{Name: }并且item.NamePraveen,所以结果将是 {Name: "Praveen" }
Adrita Sharma

是的,现在我明白了,并且在我的代码中也可以正常工作。非常感谢你@Adrita Sharma。
Praveen Sivanadiyar
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.