当一个对象的键存在于另一个对象的数组中时,在JavaScript中重新构造对象数据。

3

我有一个叫做data的对象,它具有诸如“name”、“date”等属性。

const data = {
    "name":{
      "columnName":"name",
      "columnType":"name of employee",
      "values":[
        "sam", "son"
      ],
      "range":{
        "min":0,
        "max":0
      }
    },
    "date":{
      "columnName":"date",
      "columnType":"date input",
      "categoricalValues":[
      ],
      "range":{
        "min":0,
        "max":0
      }
    },
    "fare":{
      "columnName":"fare",
      "columnType":"fare indication",
      "values":[
        "false",
        "true"
      ],
      "range":{
        "min":0,
        "max":0
      }
    },
    "id":{
      "columnName":"id",
      "columnType":"id employee",
      "values":[
      ],
      "range":{
        "min":0,
        "max":0
      }
    }
}

另一个对象categoricalColumns拥有一些属性,其中包含一个数组,在该数组中指定了前一个对象的所有属性名称。

const categoricalColumns = 
  { 
    "Charges" : ["name" , "fare"],
    "Location" : ["date", "address" ]
  }

如果对象data的属性,比如说"name"和"flare"存在于categoricalColumns的"charges"中,我需要将分类列对象重新构造成以下格式

{
    "title" : "Charges",
    "children" : [
      {
        "name":{
          "columnName":"name",
          "columnType":"name of employee",
          "values":[
            "sam", "son"
          ],
          "range":{
            "min":0,
            "max":0
          }
        }
      },
      {
        "fare":{
          "columnName":"fare",
          "columnType":"fare indication",
          "values":[
            "false",
            "true"
          ],
          "range":{
            "min":0,
            "max":0
          }
        }
      }
    ]
  }

预期结果:

const result = [
  {
    "title" : "Charges",
    "children" : [
      {
        "name":{
          "columnName":"name",
          "columnType":"name of employee",
          "values":[
            "sam", "son"
          ],
          "range":{
            "min":0,
            "max":0
          }
        }
      },
      {
        "fare":{
          "columnName":"fare",
          "columnType":"fare indication",
          "values":[
            "false",
            "true"
          ],
          "range":{
            "min":0,
            "max":0
          }
        }
      }
    ]
  },
  {
    "title" : "Location",
    "children" : [
      {
        "date":{
          "columnName":"date",
          "columnType":"date input",
          "categoricalValues":[
          ],
          "range":{
            "min":0,
            "max":0
          }
        }
      }
    ]
  },
  {
    title : "Others",
    "children" : [
      {
        "id":{
          "columnName":"id",
          "columnType":"id employee",
          "values":[
          ],
          "range":{
            "min":0,
            "max":0
          }
        }
      }
    ]
  }
]

如果 data 的某个属性与任何一个categoricalColumns不匹配,则该属性必须属于"其他"属性的子级。

3个回答

2
您可以使用一个Set来删除已访问的列。

function restructure(data, categories) {
    var others = new Set(Object.keys(data));

    return Object
        .entries(categories)
        .reduce((r, [title, category]) => {
            var children = category.filter(k => k in data).map(k => ({ [k]: data[k] }));
            if (children.length) r.push({ title, children });
            category.forEach(Set.prototype.delete, others);
            return r;
        }, [])
        .concat(others.size
            ? { title: 'Others', children: Array.from(others, k => ({ [k]: data[k] })) }
            : []
        );
}


var data = { name: { columnName: "name", columnType: "name of employee", values: ["sam", "son"], range: { min: 0, max: 0 } }, date: { columnName: "date", columnType: "date input", categoricalValues: [], range: { min: 0, max: 0 } }, fare: { columnName: "fare", columnType: "fare indication", values: ["false", "true"], range: { min: 0, max: 0 } }, id: { columnName: "id", columnType: "id employee", values: [], range: { min: 0, max: 0 } } },
    categoricalColumns = { Charges: ["name", "fare"], Location: ["date", "address"] },
    result = restructure(data, categoricalColumns);

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


它只将第一个匹配项推送到子数组中。 - RenJith
1
例如,我在children数组中看到了“name”和“fare”。 - Nina Scholz

1

const data = {
        "name": {
            "columnName": "name",
            "columnType": "name of employee",
            "values": [
                "sam", "son"
            ],
            "range": {
                "min": 0,
                "max": 0
            }
        },
        "date": {
            "columnName": "date",
            "columnType": "date input",
            "categoricalValues": [
            ],
            "range": {
                "min": 0,
                "max": 0
            }
        },
        "fare": {
            "columnName": "fare",
            "columnType": "fare indication",
            "values": [
                "false",
                "true"
            ],
            "range": {
                "min": 0,
                "max": 0
            }
        },
        "id": {
            "columnName": "id",
            "columnType": "id employee",
            "values": [
            ],
            "range": {
                "min": 0,
                "max": 0
            }
        }
    }
    const categoricalColumns = {
        "Charges": ["name", "fare"],
        "Location": ["date", "address"]
    }

    let result_obj = {};
    
    // add data elements to result_obj according to categoricalColumns:
    for (let j in data) {
        for (let k in categoricalColumns) {
            if (categoricalColumns[k].indexOf(j) > -1) {
                if (typeof result_obj[k] == 'undefined') {
                    result_obj[k] = [];
                }
                let obj = {};
                obj[data[j].columnName] = data[j];
                result_obj[k].push(obj);
                delete data[j];
                break;
            }
        }
    }
    // add remaining elements to "Others" category:
    for (let j in data) {
        if (typeof result_obj['Others'] == 'undefined') {
            result_obj['Others'] = [];
        }
        let obj = {};
        obj[data[j].columnName] = data[j];
        result_obj['Others'].push(obj);
        delete data[j];
    }
    // create result array from result_obj
    let result = [];
    for (let j in result_obj) {
        result.push({
            "title": j,
            "children": result_obj[j]
        });
    }

    console.log(result);


1
let newCategorial = [{title: 'Others', children: []}];
let index;
Object.keys(data).forEach( dataKey => {
index = '';
  for(categorialKey in Object.keys(categorialColumns)) {
     index = categorialColumns[categorialKey].indexOf(dataKey);
     if(index != -1){
       newCatIndex = newCategorial.findIndex( obj => obj.title === categorialKey);
       newCatIndex === -1? newCategorial[categorialKey].push({ title: categorialKey, children: data[dataKey]) : newCategorial[categorialKey].children.push(data[dataKey]);
     }      
  }
  if(index == -1)
     newCategorial['Others'].push(data[dataKey]);
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接