All objects contained in a std::map
(or any other standard container, for that matter) have their lifetimes managed by the container. Containers contain objects. If you want a container to contain pointers you would need to declare it as such.
For example in the following code,
struct MyType { /*...*/ };
MyType my_object;
std::map<int, MyType> my_map;
my_map.insert({42, my_object});
a copy of my_object
is made, but in the following
struct MyType { /*...*/ };
MyType my_object;
std::map<int, MyType*> my_map;
my_map.insert({42, &my_object});
the only thing that gets copied is a pointer to my_object
, not my_object
itself. In this case, the map still manages the lifetimes of its contained objects, but those contained objects are only pointers, and you are responsible for making sure the pointed-to objects outlive the pointers to them. The best way to do that is usually to use one of the standard smart pointer class templates: either std::unique_ptr
or std::shared_ptr
, depending on your needs.
For the second part of you question, yes, just having your custom comparator accept values by reference is enough. std::map
passes the actual objects contained in it to the comparator.