In C++, containers are powerful data storage arrays and they are very useful to iterate and search. A container is a holder object that stores data elements (a collection of data objects) such as std::array
, std::vector
, std::map
. There is another useful container std::multiset
, in this post, we explain what std::multiset
is. Before that let’s remind ourselves what containers are in C++ programming and what are their types. Here is a simple example of the set of int keys.
Table of Contents
What is a container in modern C++?
Containers are modern data storage arrays in modern C++ and they are very useful to iterate and search data with their amazing methods and properties.
A container is a holder object that stores data elements (a collection of data objects). They are implemented as a class template to define objects that can be used with modern rules of C++ (The rule of 6). They allow great flexibility in the different data types supported as elements. Moreover, they can be used with int, float, double, etc. or with struct types, they can be used with other modern types of C++, lambdas and templates. Thus, the developer can create different data sets in memory, these can be static or dynamic, they are safe and well optimized.
What are the basic container types modern C++?
The C++ Standards library defines 4 container types.
- Sequence Containers ( vector, array, deque, list, forward_list )
- Associative Containers ( map, multimap, set, multiset )
- Unordered Associative Containers ( unordered_map, unordered_multimap, unordered_set, unordered_multiset )
- Container Adapters ( stack, queue, priority_queue )
If you want to learn more about these each type, here are some basic details.
What is std::multiset in modern C++?
The multiset (std::multiset
) is an associative container defined in <set>
header that contains objects in a key type where key values can be the same values (multiple), and they are sorted. This container sorts members by using the Compare key comparison class. Multisets are used to list multiple key values in sorted order, i.e. { 1, 1, 4, 4, 4, 7, 7, 10}, you can search and count them easily too. Note that the std::multiset is used for multiple keys, while the std::set is used for unique keys. We can use the find method to search, the erase method to remove a member, and insert, insert_range, and emplace methods to insert new members, each of these operations has logarithmic complexity.
Here is the general definition in the header multiset.
1 2 3 |
template< class Key, class Compare = std::less< Key >, class Allocator = std::allocator< Key > > class multiset; |
since C++17, it is defined in pmr namespace as below.
1 2 3 4 5 6 |
namespace pmr { template< class Key, class Compare = std::less<Key > > using multiset = std::multiset< Key, Compare, std::pmr::polymorphic_allocator< Key > >; } |
We can use begin()
, end()
, … iterations, and ranges to operate and list them. We can use the insert
or insert_range()
method to add new key values. There are many other useful modifier methods, such as: clear()
, emplace()
, erase()
, swap()
, extract()
, merge()
operations. There are other lookup methods in addition to the find
method, such as, count
, contains
, equal_range
, etc.
Is there a simple example of how to use std::multiset in modern C++?
Here is a simple example of the multiset of int keys.
1 2 3 4 5 6 |
std::multiset<int> mymultiset { 77, 23, 1, 9, 9, 9, 7 }; mymultiset.insert(23); mymultiset.insert(50); |
As you see we define some key values and we added two more key values. Note that 23 is also defined before and it will be added as a new member of this multiset. Now, we can print all of them as we show below:
1 2 3 |
for( auto st: mymultiset) std::cout << st << ","; |
and the output will be like this:
1 2 3 |
1,7,9,9,9,23,23,50,77, |
Note that, members of std::multiset
are automatically sorted, and 23 value is added as a new member.
Let’s see another example of the set of string keys:
1 2 3 4 5 |
std::multiset<std::string> mycolors{ "Red", "Red", "Blue", "Red", "Pink" }; mycolors.insert("Blue"); |
We can list them like so:
1 2 3 |
for( auto S: mycolors) std::cout << S << " "; |
Here is the output which is automatically sorted:
1 2 3 |
Blue Blue Pink Red Red Red |
We can use find method to check if there is a member in this multiset.
1 2 3 4 |
if (auto f = mycolors.find("Blue"); f != mycolors.end()) std::cout << "Found color : " << (*f) << std::endl; |
We can count how many ”’Red” members we have in the following manner:
1 2 3 |
std::cout << "Number of red colored items: " << mycolors.count("Red") << std::endl; |
Is there a full example of how to use std::multiset in modern C++?
This example below includes all above and also if you are asking how you can use find()
method to search a key value here is how you can do it:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 |
#include <iostream> #include <set> #include <string> int main() { std::multiset<int> mymultiset { 77, 23, 1, 9, 9, 9, 7 }; mymultiset.insert(23); mymultiset.insert(50); for( auto st: mymultiset) std::cout << st << ","; std::cout << std::endl; std::multiset<std::string> mycolors{ "Red", "Red", "Blue", "Red", "Pink" }; for( auto S: mycolors) std::cout << S << " "; std::cout << std::endl; mycolors.insert("Blue"); for( auto S: mycolors) std::cout << S << " "; std::cout << std::endl; if (auto f = mycolors.find("Blue"); f != mycolors.end()) std::cout << "Found color : " << (*f) << std::endl; std::cout << "Number of red colored items: " << mycolors.count("Red") << std::endl; system("pause"); return 0; } |
Here is the output of this full example:
1 2 3 4 5 6 7 |
1,7,9,9,9,23,23,50,77, Blue Pink Red Red Red Blue Blue Pink Red Red Red Found color : Blue Number of red colored items: 3 |
Note that in this example above, if you want exact color values to list and check, you can use hexadecimal values for color values too, such as 0xAABBCC
.
As you see, multiset is a very useful container to sort multiple key values. If you want to list unique key values, then you should use set
(std::set
). If you want to use key values that point another type, then you can use std::map
or std::multimap
.
For more new details about std::set
, you can check these papers P0083R3, P0508R0
C++ Builder is the easiest and fastest C and C++ compiler and IDE for building simple or professional applications on the Windows operating system. It is also easy for beginners to learn with its wide range of samples, tutorials, help files, and LSP support for code. RAD Studio’s C++ Builder version comes with the award-winning VCL framework for high-performance native Windows apps and the powerful FireMonkey (FMX) framework for UIs.
There is a free C++ Builder Community Edition for students, beginners, and startups; it can be downloaded from here. For professional developers, there are Professional, Architect, or Enterprise versions of C++ Builder and there is a trial version you can download from here.