
上QQ阅读APP看书,第一时间看更新
How to do it...
We implement a little application that orders the placement of drivers in a fictional race in an std::map structure. While drivers pass each other during the race, we need to change their placement keys, which we do the new C++17 way.
- Let's first include the necessary headers and declare that we use namespace std.
#include <iostream>
#include <map>
using namespace std;
- We will print the race placements before and after manipulating the map structure, so let's implement a little helper function for that.
template <typename M>
void print(const M &m)
{
cout << "Race placement:\n";
for (const auto &[placement, driver] : m) {
cout << placement << ": " << driver << '\n';
}
}
- In the main function, we instantiate and initialize a map that maps from integer values that denote the driver's place to strings that contain the driver's name. We also print the map because we will modify it in the next steps.
int main()
{
map<int, string> race_placement {
{1, "Mario"}, {2, "Luigi"}, {3, "Bowser"},
{4, "Peach"}, {5, "Yoshi"}, {6, "Koopa"},
{7, "Toad"}, {8, "Donkey Kong Jr."}
};
print(race_placement);
- Let's say that during one race lap, Bowser had a little accident and dropped to the last place and Donkey Kong Jr. took the chance to jump from the last place to the third place. In that case, we first need to extract their map nodes from the map because this is the only way to manipulate their keys. The extract function is a new C++17 feature. It removes items from a map without any allocation-related side effects. Let's also open a new scope for this task.
{
auto a (race_placement.extract(3));
auto b (race_placement.extract(8));
- Now we can swap Bowser's and Donkey Kong Jr.'s keys. While the keys of map nodes are usually not mutable because they are declared const, we can modify the keys of items which we extracted using the extract method.
swap(a.key(), b.key());
- std::map's insert method got a new overload in C++17 that accepts the handles of extracted nodes, in order to insert them without touching the allocator.
race_placement.insert(move(a));
race_placement.insert(move(b));
}
- After leaving the scope, we're done. We print the new race placement and let the application terminate.
print(race_placement);
}
- Compiling and running the program yields the following output. We see the race placement in the fresh map instance first, and then we see it again after swapping Bowser's and Donkey Kong Jr.'s positions.
$ ./mapnode_key_modification
Race placement:
1: Mario
2: Luigi
3: Bowser
4: Peach
5: Yoshi
6: Koopa
7: Toad
8: Donkey Kong Jr.
Race placement:
1: Mario
2: Luigi
3: Donkey Kong Jr.
4: Peach
5: Yoshi
6: Koopa
7: Toad
8: Bowser