I have an unordered_map which stores the int as key an pointer as value. I need to check the existence of the key. If the key is not available, I need to insert the key and value. Which one is the better approach?
Thanks.
unordered_map<int, classA*>testMap;
classA* ptr = testMap[1];
if(ptr == NULL)
testMap[1] = new classA;
OR
unordered_map<int, classA*>::iterator it = testMap.find(1);
if(it == testMap.end())
{
testMap.insert(make_pair(1, new classA));
}
Neither method is good because both use two queries into the map where one would be sufficient.
A better method is retrieving a reference to the element, and if that reference is a null pointer, assign to it:
classA*& ptr = testMap[1];
if (ptr == 0)
ptr = new classA;
This works because querying a non-existing element in a map automatically inserts it (default-constructed, thus a null pointer will be inserted), and operator[]
returns a reference to that element (be it newly created or already existing).
But notice that the semantics between this method (or your first method) and your second method subtly differ: your second method only inserts the element if the key doesn’t exist in the map. My method (and your first method) also create a new element if the key in fact already existed, but its value was a null pointer.
The second is the better approach. In the first, when you do classA* ptr = testMap[1]
, you are creating an item in the hash with the default value of NULL
.
If you were to change the map value to something other than a pointer (maybe a vector
for example) then you might not have a suitable default value to test against. Also, in the future, NULL
might be a valid value for your map, so your default value test would be meaningless.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With