Home > Software engineering >  How to add a number to the name of an item that already exists in a json object before adding it to
How to add a number to the name of an item that already exists in a json object before adding it to

Time:09-19

Basically, I have an JSON Object named map, to which I add a key and value whenever it is needed for temporary storage. So I need a function that checks if the key already exists in map and if it does exist then it adds a number to end of the key's name like _(number) and the number increases for every duplicate.

i.e (Just an example, I'm using the map for different purposes)

{
   "hello": "world",
   "hello_(1)": "do you like pizza?",
   "hello_(2)": "https://google.com/"
}

Please do help me, Thanks!

CodePudding user response:

Try to use Map.

(almost) One liner

Here is a short snippet:

var myMap = new Map();
myMap.has("hello") ? myMap.get("hello").push("newValueForHello") : myMap.set("hello", ["newValueForHello"])

Multi lines

The above is not very readable so I'll also add a more readable snippet but does the exact same thing

// Create the map instance
var myMap = new Map();

// if the map instance already has a "hello" key
if(myMap.has("hello") {
  // get the key (which must be an array) and push the new value to the array.
  myMap.get("hello").push("newValueForhello")
} else {
  // if the map doesn't have the "hello" key, the add an empty array.
  myMap.set("hello", ["newValueForHello"])
}

As a function

Here it is as a function..

function addItemToMap(mapObj, key, value) {
  // if the key doesn't exist yet..
  if(!mapObj.has(key)) {
    // initialize it to an empty array.
    mapObj.set(key, [])
  }
  
  // At this point the key must exist, and it must be an array, so just push a new item to the array.
  mapObj.get(key).push(value)
}

// usage 
var myMap = new Map()
addItemToMap(myMap, "hello", "first hello item")
addItemToMap(myMap, "hello", "second hello item")

CodePudding user response:

Here is a solution to your question:

const myDictionary = {
    "hello": "hello",
    "bye": "bye"
}

const addItemToDictionary = (newKey, newVal, dict) => {
    const keyRegExp = new RegExp(`^${newKey}\.*`)
    const keyCount = Object.keys(dict).filter(key => keyRegExp.test(key)).length;
    return ({
        ...dict,
        [`${newKey}_(${keyCount})`]: newVal
    })
}

console.log(
    addItemToDictionary('hello', 'hello yet again',
        addItemToDictionary('bye', 'bye again',
            addItemToDictionary('hello', 'hello again', myDictionary)
        )
    )
);

Bare in mind there is a lot of edge cases that you can have, eg. your new key can be 'hell' and it will break this solution (this is just one of many).

In such a situations as an engineer you should rethink your approach.

I would suggest instead of adding new elements to json as you asked you can simply change data structure interface:

const myDictionary = {
    "hello": "hello",
    "bye": "bye"
}

const addItemToDictionary = (newKey, newVal, dict) => {
    const dictEntry = Object.keys(dict).find(key => key === newKey);
    return ({
        ...dict,
        [newKey]: dictEntry ? [...[dictEntry], newVal] : newVal
    })

}


console.log(
    addItemToDictionary('hello', 'hello yet again',
        addItemToDictionary('bye', 'bye again',
            addItemToDictionary('hello', 'hello again', myDictionary)
        )
    )
);

  • Related