-
-
Save ufna/89e07e841160d4a1dbefaa1886c66653 to your computer and use it in GitHub Desktop.
Demonstrate usage of noncopyable class in std containers
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// http://stackoverflow.com/questions/17603666/copy-move-requirements-for-the-key-value-types-in-a-stdmap | |
#include <map> | |
#include <vector> | |
struct foo | |
{ | |
int i; | |
foo(int j) : i(j) {} | |
// make foo non-copyable | |
foo(const foo &) = delete; // copy ctor | |
foo & operator=(const foo &) = delete; // assignment op | |
// Use default move ctors. You have to declare these, otherwise the | |
// class will not have automatically generated move ctors. | |
foo (foo && other) = default; | |
foo & operator=(foo &&) = default; | |
}; | |
// Required for foo to be used as a key in std::map | |
bool operator<(const foo & f1, const foo & f2) | |
{ | |
return f1.i < f2.i; | |
} | |
int main(int argc, char ** argv) | |
{ | |
// Test whether we can create a map where keys are non-copyable. We | |
// can, but the map itself cannot be copied (makes sense). | |
{ | |
std::map<foo,int> f; | |
// std::map<foo,int> f2 = f; // compile error - can't copy map with uncopyable items | |
std::map<foo,int> f3 = std::move(f); // OK: when moving, nothing is copied | |
} | |
// Test whether we can create a map where values are non-copyable. | |
{ | |
std::map<int, foo> f; | |
std::map<int, foo> f3 = std::move(f); // OK: when moving, nothing is copied | |
} | |
// Test inserting noncopyable keys into the map. | |
{ | |
std::map<foo, int> f; | |
f.insert(std::make_pair(foo(1), 1)); // works if foo has move ctor | |
f[foo(1)] = 1; // works if foo has move ctor | |
f.emplace(std::make_pair(foo(1), 1)); // works if foo has move ctor | |
f.emplace(foo(1), 1); // works if foo has move ctor | |
} | |
// Test non-copyable items in std::vector. | |
{ | |
std::vector<foo> f; | |
f.push_back(foo(1)); // works if foo has move ctor | |
f.emplace_back(foo(1)); // works if foo has move ctor | |
f.emplace_back(1); // works by forwarding the arg to the foo ctor | |
} | |
return 0; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment