Q:

C++ pass pointers to a Template class function

I am new to C++ (more of a java guy). I am trying to teach myself about C++ pointers. Here I've created two classes, Person (The base class), and the Student (Derived class).
I tried to put Student objects in an unordered_map<string, Person>. But met an error.
This is my code:
class Person
{
  protected:
    string name;
    int age;

  public:
    int getAge()
    {
      return age;
    }
    string getName()
    {
      return name;
    }
};

class Student : public Person
{
  private:
    string grade;

  public:
    Student(string const &name, int const &age, string const &grade)
    {
      this -> name = name;
      this -> age = age;
      this -> grade = grade;
    }
    int getAge();
};

Here's my main function:
int main()
{
  unordered_map<string, Person *> students;
  Student s("Sam", 26, "A");
  Person *p;
  p = &s;

  students.insert(p -> getName(), p);

  return 0;
}

This is just a part of the code, and I know it looks foolish. But I'm just learning about pointers
I have included <iostream> and <unordered_map> libraries and using namespace std here.
Error message is so long. Can someone point out the error I made here ? Or, should I post that long error message also ?
Thanks in advance.

A:

I am more of a java guy.

Here's what you need to know:
Pointers
Person* is a pointer to a person - a pointer simply carries the address of an object in memory. It's as low level as you can get. It's equivalent to using an address register or index register in assembly language. It carries no information about object lifetime and does not influence object lifetime in any way. It is 100% abusable. Use with care, if ever.
Shared references
// java code
var x = new Y();
var y = x;

// equivalent c++
auto x = std::make_shared<Y>();
auto y = x;

If you want java-like behaviour, then std::shared_ptr<Person> is equivalent to a java object reference. It shares ownership of the person and allows (actually in c++ mandates) that the Person is destroyed when all of the shared_ptrs have gone out of scope or have been reset.
Unique reference with lifetime control
Between the two is a std::unique_ptr<Person> which will cause the automatic destruction of the Person when the one and only unique_ptr is destroyed or reset. You cannot copy a std::unique_ptr so it can't be used to share references to an object. It can however, be converted to a shared_ptr (this implicitly empties the unique_ptr).
Weak references
Then there is a std::weak_ptr<Person> which is the weak counterpart to a std::shared_ptr<Person>. It cannot be de-referenced directly but must first be converted to a shared_ptr with the lock() method. This provides an atomic 'test for existence and lock into place' operation. We use it to resolve or avoid resource leaks caused by circular references (which java claims not to have on account of garbage collection).
Lifetime differences between Java and C++
In Java, when there are no more reachable references to an object, it becomes a candidates for garbage collection. At some point in the future, it may or may not be recovered.
C++ is different and more predictable. When the unique_ptr or the last shared_ptr controlling an object's lifetime is reset, that object's destructor will be executed immediately and in the same thread. It's completely sequential. This gives rise to the possibility of RAII, and allows us to use object lifetimes to cause code to execute no matter what the execution path.
This is also arguably why there is no need for finally in c++. Resource cleanup goes in the destructors of resource owners.

