【问题标题】:How to add a new item to an object at a specific position with vanilla JS如何使用 vanilla JS 将新项目添加到特定位置的对象
【发布时间】:2021-04-09 21:11:27
【问题描述】:

最初,我有这样一个对象

里面数据比较多,我错过了

"Citizens": [

            {
                "_id": "6070be28c98d5a0ea88f131c",
                "id": 1,
                "name": "Karl",
                "city_id": "1",
                "groups": []
            },
          ]

在这个循环中经过它之后

                       for(let i = 0; i < objTmp[0]["Citizens"].length; i++){
                            for(let j = 0; j < citiesAll[0]["Cities"].length; j++){
                                if(objTmp[0]["Citizens"][i].id == citiesAll[0]["Cities"][j].id) {

           
                                  objTmp[0]["Citizens"][i].city = citiesAll[0]["Cities"][j];


                                }       
                            }
                        }

我从另一个对象中添加一个城市对象

我得到了这样一个对象

“公民”: [

        {
            "city": {
                "id": 1,
                "name": "Moscow",
                "data": "10000000"
            },
            "_id": "6070be28c98d5a0ea88f131c",
            "id": 1,
            "name": "Karl",
            "city_id": "1",
            "groups": []
        },

]

问题?

我怎样才能不将城市添加到开头,如此处所示,而是添加到末尾?

【问题讨论】:

  • 对象属性没有顺序。它不像一个数组。
  • 他们确实有命令,但并不总是强制执行。见:Does ES6 introduce a well-defined order of enumeration for object properties?
  • objects真的是乱序了,但一定有办法在最后加city?
  • 没有办法将其添加到末尾。无论城市在起点还是终点还是中间,都是同一个对象。
  • 现在正在研究解决方案。敬请期待……

标签: javascript for-loop object


【解决方案1】:

正如 Roshan 所说,关键命令在 JS 中是不可靠的,因此不应该依赖它。如果您需要维护密钥顺序,我建议使用地图。

以下是两者的示例(包括不可靠的对象路由):

1。作为一个对象

因为对象键没有固有顺序,如果您在浏览器控制台中运行它并展开您的对象,这可能看起来不正确,但如果您运行下面的 sn-p,您将在您的安慰。为了确保所需的顺序,请使用地图,在第 2 节中进一步解释。

1.1。作为使用嵌套数组方法循环的对象

const objTmp = [{ Citizens: [{ _id: "6070be28c98d5a0ea88f131c", id: 1, name: "Karl", city_id: "1", groups: [] }]}];
const citiesAll = [{ Cities: [{ id: 1, name: "Moscow", data: "10000000" }]}];

objTmp[0]["Citizens"].forEach((citizen, i) => citiesAll[0]["Cities"].find(city => city.id && citizen.id && city.id === citizen.id && (objTmp[0]["Citizens"][i] = { ...citizen, city: { ...city } } )))

console.log(objTmp[0]["Citizens"][0]);

1.2。作为使用嵌套for 循环的对象

const objTmp = [{ Citizens: [{ _id: "6070be28c98d5a0ea88f131c", id: 1, name: "Karl", city_id: "1", groups: [] }]}];
const citiesAll = [{ Cities: [{ id: 1, name: "Moscow", data: "10000000" }]}];

for (let i = 0; i < objTmp[0]["Citizens"].length; i++) {
    for (let j = 0; j < citiesAll[0]["Cities"].length; j++) {
        if (objTmp[0]["Citizens"][i].id && citiesAll[0]["Cities"][j].id && objTmp[0]["Citizens"][i].id === citiesAll[0]["Cities"][j].id) {
            objTmp[0]["Citizens"][i] = { ...objTmp[0]["Citizens"][i], city: { ...citiesAll[0]["Cities"][j] } };
            break;
        }
    }
}

console.log(objTmp[0]["Citizens"][0]);

1.3。作为使用嵌套for..of 循环的对象

const objTmp = [{ Citizens: [{ _id: "6070be28c98d5a0ea88f131c", id: 1, name: "Karl", city_id: "1", groups: [] }]}];
const citiesAll = [{ Cities: [{ id: 1, name: "Moscow", data: "10000000" }]}];

{
    let i = 0;
    for (citizen of objTmp[0]["Citizens"]) {
        let j = 0;
        for (city of citiesAll[0]["Cities"]) {
            if (city.id && citizen.id && city.id === citizen.id) {
                objTmp[0]["Citizens"][i] = { ...citizen, city: { ...city } };
                break;
            }
            j++;
        }
        i++;
    }
}

console.log(objTmp[0]["Citizens"][0]);

2。作为地图

这个你需要在浏览器的控制台中运行,因为 StackOverflow 的控制台不能打印 JS Map 数据。

2.1。作为使用嵌套数组方法循环的 Map

// I am only using this replacer function to support logging the result Map data to the console properly. This function is not require for production-use.
const replacer = (a,e) => e instanceof Map?{dataType:"Map",value:Array.from(e.entries())}:e;

const objTmp = [{ Citizens: [{ _id: "6070be28c98d5a0ea88f131c", id: 1, name: "Karl", city_id: "1", groups: [] }]}];
const citiesAll = [{ Cities: [{ id: 1, name: "Moscow", data: "10000000" }]}];

objTmp[0]["Citizens"].forEach((citizen, i) => (objTmp[0]["Citizens"][i] = new Map(Object.entries(citizen)), citiesAll[0]["Cities"].find(city => city.id && objTmp[0]["Citizens"][i].get('id') && city.id === objTmp[0]["Citizens"][i].get('id') && (objTmp[0]["Citizens"][i].set('city', { ...city })))));

console.log(JSON.stringify(objTmp[0]["Citizens"][0], replacer, 2));

2.2.作为使用嵌套 for 循环的 Map

// I am only using this replacer function to support logging the result Map data to the console properly. This function is not require for production-use.
const replacer = (a,e) => e instanceof Map?{dataType:"Map",value:Array.from(e.entries())}:e;

const objTmp = [{ Citizens: [{ _id: "6070be28c98d5a0ea88f131c", id: 1, name: "Karl", city_id: "1", groups: [] }]}];
const citiesAll = [{ Cities: [{ id: 1, name: "Moscow", data: "10000000" }]}];

for (let i = 0; i < objTmp[0]["Citizens"].length; i++) {
    objTmp[0]["Citizens"][i] = new Map(Object.entries(objTmp[0]["Citizens"][i]));
    for (let j = 0; j < citiesAll[0]["Cities"].length; j++) {
        if (citiesAll[0]["Cities"][j].id && objTmp[0]["Citizens"][i].get('id') && citiesAll[0]["Cities"][j].id === objTmp[0]["Citizens"][i].get('id')) {
            objTmp[0]["Citizens"][i].set('city', { ...citiesAll[0]["Cities"][j] });
            break;
        }
    }
}

console.log(JSON.stringify(objTmp[0]["Citizens"][0], replacer, 2));

2.3。作为使用嵌套 for..of 循环的 Map

// I am only using this replacer function to support logging the result Map data to the console properly. This function is not require for production-use.
const replacer = (a,e) => e instanceof Map?{dataType:"Map",value:Array.from(e.entries())}:e;

const objTmp = [{ Citizens: [{ _id: "6070be28c98d5a0ea88f131c", id: 1, name: "Karl", city_id: "1", groups: [] }]}];
const citiesAll = [{ Cities: [{ id: 1, name: "Moscow", data: "10000000" }]}];

{
    let i = 0;
    for (citizen of objTmp[0]["Citizens"]) {
        objTmp[0]["Citizens"][i] = new Map(Object.entries(citizen));
        let j = 0;
        for (city of citiesAll[0]["Cities"]) {
            if (city.id && objTmp[0]["Citizens"][i].get('id') && city.id === objTmp[0]["Citizens"][i].get('id')) {
                objTmp[0]["Citizens"][i].set('city', { ...city });
                break;
            }
            j++;
        }
        i++;
    }
}

console.log(JSON.stringify(objTmp[0]["Citizens"][0], replacer, 2));

【讨论】:

  • 如何使这个结构在嵌套循环中工作?
  • @Cooler-cpu 我已经更新了我的解决方案,除了数组forEach() 方法循环之外,还包括经典for 循环和for..of 循环的示例。请检查并尝试每一个。请记住,地图将可靠地保持顺序,而对象则不会。为了测试地图解决方案(2.1、2.2 和 2.2),您需要在控制台中运行代码,因为 StackOverflow 目前不支持将地图数据记录到其内置控制台。
【解决方案2】:

我不得不不同意其他提供对象键排序方法的答案。

我的回答:不要那样做。尝试对 JavaScript 对象的键进行排序是不好的做法,而且是反语义的。阅读您的代码的人要么会感到困惑,要么会正确地认为它充满了错误。

我完全认识到 will have a de-facto order 的密钥,但我提供的是您不应该依赖它的意见

使用地图或元组或其他构建来进行排序的东西。

【讨论】:

  • 我的答案是目前唯一的其他答案,我特别说不要重新排序 Object 键并改用 Map,我提供了具体的指导和示例,所以我不是确定您指的是哪些其他答案。
猜你喜欢
  • 1970-01-01
  • 2021-12-17
  • 2011-11-11
  • 2019-10-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-09-26
相关资源
最近更新 更多