Anurak Jairak
Anurak Jairak

Reputation: 25

How can I merge duplicate keys in a JavaScript object?

I have a JavaScript object as follows :

{
    "zone": [{
        "$origin": "domainname.com.",
        "a": [{
                "name": "ironman",
                "ip": "192.168.0.1"
            }, {
                "name": "thor",
                "ip": "192.168.0.2"
            },
            {
                "name": "odin",
                "ip": "192.168.0.3"
            }
        ]

    }, {
        "$origin": "domainname.com.",
        "a": [{
                "name": "javis",
                "ip": "192.168.0.4"
            },
            {
                "name": "jump",
                "ip": "192.168.0.5"
            },
            {
                "name": "jupiter",
                "ip": "192.168.0.6"
            }
        ]
    }]
}

I want to merge duplicate key in "$origin" and append value in "a" key

{
    "zone": [{
        "$origin": "domainname.com.",
        "a": [{
                "name": "ironman",
                "ip": "192.168.0.1"
            }, {
                "name": "thor",
                "ip": "192.168.0.2"
            },
            {
                "name": "odin",
                "ip": "192.168.0.3"
            },
            {
                "name": "javis",
                "ip": "192.168.0.4"
            },
            {
                "name": "jump",
                "ip": "192.168.0.5"
            },
            {
                "name": "jupiter",
                "ip": "192.168.0.6"
            }
        ]

    }]
}

I know how to merge duplicate keys from two different object from other topics, but I don't know how to merge and find duplicate keys in the same object.

Upvotes: 1

Views: 3468

Answers (2)

brk
brk

Reputation: 50291

You can loop through the array starting from index 1 and keep on pushing the values in the object at index 0

let x = {
  "zone": [{
    "$origin": "domainname.com.",
    "a": [{
        "name": "ironman",
        "ip": "192.168.0.1"
      }, {
        "name": "thor",
        "ip": "192.168.0.2"
      },
      {
        "name": "odin",
        "ip": "192.168.0.3"
      }
    ]

  }, {
    "$origin": "domainname.com.",
    "a": [{
        "name": "javis",
        "ip": "192.168.0.4"
      },
      {
        "name": "jump",
        "ip": "192.168.0.5"
      },
      {
        "name": "jupiter",
        "ip": "192.168.0.6"
      }
    ]
  }]
}
// starting to loop from index 1, new elements will be pushed
  to the object at index 0
for (var i = 1; i < x.zone.length; i++) {
  // looping through the array of object at index 1 ...
  x.zone[i].a.forEach(function(item) {
    // dummy object which will have values from other objects
    let dumObj = {};
    dumObj.name = item.name;
    dumObj.ip = item.ip;
    
    x.zone[0].a.push(dumObj);
  })
}

console.log(x)

Upvotes: 0

kevguy
kevguy

Reputation: 4438

First of all, use reduce to collect the duplicates and save them in a temporary object with values of $origin as its keys. Then iterate the keys and reconstruct the the object.

Another way would be doing most of the work in the reduce method with some filtering but I think my current solution is faster.

const data = {
    "zone": [{
        "$origin": "domainname.com.",
        "a": [{
                "name": "ironman",
                "ip": "192.168.0.1"
            }, {
                "name": "thor",
                "ip": "192.168.0.2"
            },
            {
                "name": "odin",
                "ip": "192.168.0.3"
            }
        ]

    }, {
        "$origin": "domainname.com.",
        "a": [{
                "name": "javis",
                "ip": "192.168.0.4"
            },
            {
                "name": "jump",
                "ip": "192.168.0.5"
            },
            {
                "name": "jupiter",
                "ip": "192.168.0.6"
            }
        ]
    },
    {
        "$origin": "eomainname.com.",
        "a": [{
                "name": "javis",
                "ip": "192.168.0.4"
            },
            {
                "name": "jump",
                "ip": "192.168.0.5"
            },
            {
                "name": "jupiter",
                "ip": "192.168.0.6"
            }
        ]
    }]
}

const result = { zone: [] }
const tmp = data.zone.reduce((acc, curr) => {
  if (acc.hasOwnProperty(curr.$origin)) {
    acc[curr.$origin] = acc[curr.$origin].concat(curr.a)
  } else {
    acc[curr.$origin] = curr.a
  }
  return acc;
}, {})

result.zone = Object.keys(tmp).map((key) => {
  return {
    $origin: key,
    a: tmp[key]
  }
})

console.log(result)

Upvotes: 1

Related Questions