title: Why am I able to dereference a pointer to an abstract class?
body: <p>In the code below, <code>IContainer</code> is a pure abstract class: it does not contain any methods which are not pure virtual. This being the case, I don't expect to be able to instantiate an object of type <code>IContainer</code>, however I do expect to be able to hold an instance of a derived class in an <code>IContainer*</code>.</p>
  
  <p>In <code>main</code> below, I have created some instances of the concrete class <code>SimpleContainer</code> which implements <code>IContainer</code>. Next, I have stored a pointer to these <code>SimpleContainer</code>s in some <code>IContainer*</code> variables.</p>
  
  <p>Here is my question: since <code>IContainer</code> is an abstract class, I cannot instantiate it. However, at the bottom of my <code>main</code> you can see that I dereference my <code>IContainer</code> pointers in order to check equality. Why am I able to do this? Also, is there any difference between <code>iCont1 == iCont2</code> and <code>*iCont1 == *iCont2</code>?</p>
  
  <pre><code>#include &lt;iostream&gt;
  
  class IContainer{
      public:
          virtual bool operator==(const IContainer&amp; aICont) const = 0;
          virtual int getVal() const = 0;
  };
  
  class SimpleContainer : public IContainer{
      public:
          SimpleContainer(int val) : val(val){};
          int getVal() const override {return val;}
          bool operator==(const IContainer&amp; aICont) const override
          {
              return val == aICont.getVal();
          }
      private:
          int val;
  };
  
  int main(){
      SimpleContainer cont1(1), cont2(2), cont3(1);
      IContainer* iCont1 = &amp;cont1;
      IContainer* iCont2 = &amp;cont2;
      IContainer* iCont3 = &amp;cont3;
  
      std::cout &lt;&lt; "iCont1 == iCont2 -&gt; " &lt;&lt; (iCont1 == iCont2 ? "true" : "false") &lt;&lt; " || Expecting -&gt; " &lt;&lt; "false" &lt;&lt; std::endl;        
      std::cout &lt;&lt; "*iCont1 == *iCont2 -&gt; " &lt;&lt; (*iCont1 == *iCont2 ? "true" : "false") &lt;&lt; " || Expecting -&gt; " &lt;&lt; "false" &lt;&lt; std::endl; 
      std::cout &lt;&lt; "iCont1 == iCont3 -&gt; " &lt;&lt; (iCont1 == iCont3 ? "true" : "false") &lt;&lt; " || Expecting -&gt; " &lt;&lt; "false" &lt;&lt; std::endl; 
      std::cout &lt;&lt; "*iCont1 == *iCont3 -&gt; " &lt;&lt; (*iCont1 == *iCont3 ? "true" : "false") &lt;&lt; " || Expecting -&gt; " &lt;&lt; "false" &lt;&lt; std::endl; 
      return 0;
  }  
  </code></pre>