MAPS In STL

Get Ready To Explore MAPS In STL In Detail.

Until now, we have seen most of the STL containers having a single data type. In this tutorial, we will begin discussing the associative containers in STL. The first such container is “Map”.

The map is an associative container having a key-value pair such that the key values are always unique. Key in the map can be inserted or deleted but it cannot be changed. On the other hand, the values associated with keys can be changed.

=> Read Through The Easy C++ Training Series.

MAPS IN STL

In a map, keys are always sorted. Data types of key and value can be anything from standard to user-defined data types.

Let's Explore!!

Declaration And Initialization

In STL, in order to implement map we need to include a <map> header in our program.

#include<map>

The general syntax of map declaration is as follows:

map<key type, value type> map_name;

Here, key type and value type are the data types of keys and values respectively.

Using the above general syntax, we can declare a map of integer keys and values as follows:

map<int, int> mymap;

Now, we can initialize the map during declaration itself.

This is done as follows:

map<int, int> mymap {{1, 10}, {2, 20}, {3, 30}};

The above line of code initializes the map with three key-value pairs.

Note that in the map, key and its corresponding value is always initialized or inserted in pair. We can never add it as the only key or only value.

Operations

In this topic, we will discuss some basic operations of the map.

  • at and [ ]: Operators at and [ ] are used for accessing the map elements. Both at and [] have the same functionality with one difference. If the accessed key is not present in the map then the ‘atoperator throws an exception. Whereas [ ] operators inserts a new key in the map if the accessed key is not present in the map.
  • begin: Returns an iterator to the first element in the map.
  • end: Returns an iterator pointing to the element after the last element in the map.

Let us see the below Example on the usage of at and [ ] as well as begin/end function.

#include <iostream>
#include <map>
using namespace std;
int main()
 {
   map<int, int> mymap {{1,10},{2,20},{3,30}};
   //display the map
   map<int,int> :: iterator it;
   cout << "\nThe map mymap is : \n";
   cout << "\tKEY\tVALUE\n";
     for (it = mymap.begin(); it != mymap.end(); ++it) {
        cout << '\t' << it->first
        << '\t' << it->second << '\n';
 }
cout << endl;
mymap.at(2) = 10; //change value of second element
mymap[3] = 10; //change value of third element
//display the map
cout << "\nThe map mymap is : \n";
cout << "\tKEY\tVALUE\n";
for (it = mymap.begin(); it != mymap.end(); ++it) {
     cout << '\t' << it->first
     << '\t' << it->second << '\n';
   }
cout << endl;
}

Output:

The map mymap is :

KEY    VALUE

1              10
2             20
3             30

The map mymap is :

KEY    VALUE

1             10
2            10
3            10

So in the above code, we have a map mymap with key, value pair of type integer. We have initialized it to three elements. We display this map using the iterator functions begin and end.

Then using the “at” operator we change the value of the second value and using the [ ] operator we alter the value of the third element such that now all three elements have a value 10. This is evident when we display the map again after altering the values.

  • insert(key, value) : Inserts a new element (key, value pair) in the map.
  • erase: This operation is used to remove an element from the map. It has two versions.
    • erase(position) – Here we give the position pointed by the iterator and element at that position is removed.
    • erase(key) – We can also specify a key of the particular element as the argument to erase function and the element having that particular key value will be removed.
  • empty: Checks if the map is empty.
  • size: Returns the size of the map i.e. the number of elements in the map.
  • max_size: Returns the maximum size the map can hold.
  • clear: Removes all elements from the map.

Here is an example code where we will demonstrate the usage of these functions.

#include <iostream>
#include <map>
using namespace std;
int main()
{
   map<int,int> mymap;
   mymap.insert(pair<int, int>(1, 1));
   mymap.insert(pair<int, int>(2, 3));
   mymap.insert(pair<int, int>(3, 5));
   mymap.insert(pair<int, int>(4, 7));
   mymap.insert(pair<int, int>(5, 9));
   mymap.insert(pair<int, int>(6, 11));
   mymap.insert(pair<int, int>(7, 13));
   //display the map
   map<int,int> :: iterator it;
   cout << "\nThe map mymap is : \n";
   cout << "\tKEY\tVALUE\n";
   for (it = mymap.begin(); it != mymap.end(); ++it) {
      cout << '\t' << it->first
      << '\t' << it->second << '\n';
      }
   cout << endl;
   cout<<"\n mymap.size(): "<<mymap.size();
   cout<<"\n mymap.max_size(): "<<mymap.max_size();
   cout<<endl;
   int num;
   num = mymap.erase(3);
   cout << "\nmymap.erase(3) : ";
   cout << num << " removed \n";
   cout << "\tKEY\tELEMENT\n";
   for (it = mymap.begin(); it != mymap.end(); ++it) {
      cout << '\t' << it->first
      << '\t' << it->second << '\n';
      }
   cout << endl;
   mymap.clear();
   cout<<"\nAfter clear operation mymap.size() : "<<mymap.size();
}

Output:

The map mymap is :

KEY           VALUE

1                      1

2                     3

3                     5

4                     7

5                     9

6                    11

7                    13

mymap.size(): 7

mymap.max_size(): 461168601842738790

mymap.erase(3) : 1 removed

KEY      ELEMENT

1                    1

2                   3

4                   7

5                   9

6                  11

7                  13

After clear operation mymap.size() : 0

Screenshot for the output is given below.

multimap output

In this program, we have shown the usage of various functions with respect to the map. We see that after erase operation, the size of the map reduces by 1 and it becomes 0 when clear is executed.

With this, we come to the end of our discussion on the map. Next, we discuss the two variants of the map i.e. the multimap and unordered map.

Multimap

Multimap is similar to the map in most aspects. The only difference is that it is allowed to have multiple elements having the same key. Hence, it is not required that the key must be unique but it is required that key-value pair must be unique.

The operations that we discussed above for map also hold for multimap.

Here we modify the above example to demonstrate Multimap.

#include <iostream>
#include <map>
using namespace std;
int main()
{
   multimap<int,int> mymap;
   mymap.insert(pair<int, int>(1, 1));
   mymap.insert(pair<int, int>(2, 3));
   mymap.insert(pair<int, int>(3, 5));
   mymap.insert(pair<int, int>(3, 7));
   mymap.insert(pair<int, int>(4, 9));
   //display the map
   map<int,int> :: iterator it;
   cout << "\nThe multimap mymap is : \n";
   cout << "\tKEY\tVALUE\n";
   for (it = mymap.begin(); it != mymap.end(); ++it) {
      cout << '\t' << it->first
      << '\t' << it->second << '\n';
      }
   cout << endl;
   cout<<"\n mymap.size(): "<<mymap.size();
   cout<<"\n mymap.max_size(): "<<mymap.max_size();
   cout<<endl;
   int num;
   num = mymap.erase(3);
   cout << "\nmymap.erase(3) : ";
   cout << num << " removed \n";
   cout << "\tKEY\tELEMENT\n";
   for (it = mymap.begin(); it != mymap.end(); ++it) {
      cout << '\t' << it->first
      << '\t' << it->second << '\n';
     }
   cout << endl;
   mymap.clear();
   cout<<"\nAfter clear operation mymap.size() : "<<mymap.size();
}

Output:

The multimap mymap is :

KEY           VALUE

1                      1

2                     3

3                     5

3                     7

4                     9

mymap.size(): 5

mymap.max_size(): 461168601842738790

mymap.erase(3) : 2 removed

KEY          ELEMENT

1                        1

2                       3

4                       9

After clear operation mymap.size() : 0

Screenshot for the same is given below:

Output of multimap mymap

In this program to demonstrate the multimap, we have defined a multimap and then using the insert operation, we have inserted the values in this multimap. Then we display the multimap.

Notice that in multimap, we have two elements with the same key=3. But as it’s a multimap this is allowed as long as the key-value pair is unique. Then we display the size and max_size of the multimap.

Next, we call the erase operation on multimap with key=3. Now as there are two entries with the same key, note that erase operation removed two elements from the multimap.

Now we will take a look at another variant of map i.e. unordered_map.

Unordered Map

Similar to the map, the unordered map is an associative container that is used to store keys and corresponding values. But in contrast to map which is always sorted, in the unordered map as the name suggests the elements or keys can be in order.

As in the map, the key value is used to uniquely identify the element. Data types of key and mapped value can be either predefined or user-defined.

The internally unordered map is implemented as a “Hash Table” data structure, the key provided to map is hashed into indices in the hash table. Hence the performance of data structure depends a lot on the hash function provided.

The general declaration of the unordered map is:

unordered_map<keyType, valueType> umap_name;

The header to include, in order to implement unordered_map is <unordered_map>.

Let us discuss some operations that unordered_map support for accessing & manipulating elements.

  • begin: Returns a reference to the first element in the unordered map.
  • end: Points to the element followed by the last element in the unordered map.
  • at: Returns a reference to the value with respect to key k.
  • bucket: Returns the bucket number of elements with key k that is located on the map.
  • bucket_count: Returns the total number of buckets in the unordered map.
  • bucket_size: Returns the number of elements in each bucket.
  • count: Returns the number of elements present in an unordered map for a given key

Let see a code example to check the usage of Unordered map operations.

#include <iostream> 
#include <unordered_map> 
using namespace std; 
  int main() 
{     
    unordered_map<string, int> umap; 
  
     //insert values using [] 
    umap["RED"] = 1; 
    umap["GREEN"] = 2; 
    umap["BLUE"] = 3; 
    
    // inserting value by insert function 
    umap.insert(make_pair("YELLOW", 4)); 
  
    unordered_map<string, int>:: iterator it; 
    cout << "\nAll Elements in unordered map umap : \n"; 
    for (it = umap.begin(); it != umap.end(); ++it) 
    { 
        
        cout << it->first << "  " << it->second << endl; 
    } 
    
    cout<<"\numap bucket_count : "<<umap.bucket_count();
    cout<<"\nbucket_size : "<<umap.bucket_size(2);
}

Output:

All Elements in unordered map umap :
YELLOW 4
BLUE 3
GREEN 2
RED 1

umap bucket_count : 11
bucket_size : 0

The screenshot for the same is given below.

unordered map - Output

In the above code, we declare an unordered map and insert values into it using the [ ] operator and insert operation. Then we display the map using iterators.

We also call operations “bucket_count” which gives the total number of buckets in this particular unordered map(this is internal calculation) and also “bucket_size” for key value=2.

Conclusion

With this, we have come to the end of this tutorial on STL Map.

In our upcoming tutorial, we will be looking into the details of our last STL container “Set”.

=> Check Out The Best C++ Training Tutorials Here.