title: Acceptable to use virtual inheritance to prevent accidentally creating a diamond?
body: <p>This is a simplification of some real code, and a real mistake I made when I didn't realize someone else had already implemented Foo and derived from it.</p>
  
  <pre><code>#include &lt;iostream&gt;
  
  struct Base {
     virtual ~Base() { }
     virtual void print() = 0;
  };
  
  struct OtherBase {
     virtual ~OtherBase() { }
  };
  
  struct Foo : public Base { // better to use virtual inheritance?
     virtual void print() { std::cout &lt;&lt; "Foo" &lt;&lt; std::endl; };
  };
  
  struct Bar : public Base { // better to use virtual inheritance?
     virtual void print() { std::cout &lt;&lt; "Bar" &lt;&lt; std::endl; };
  };
  
  // The design is only supposed to implement Base once, but I
  // accidentally created a diamond when I inherited from Bar also.
  class Derived
     : public OtherBase
     , public Foo
     , public Bar // oops.
  {
  };
  
  int main() {
     Derived d;
     OtherBase *pO = &amp;d;
  
     // cross-casting
     if (Base *pBase = dynamic_cast&lt;Base *&gt;(pO))
        pBase-&gt;print();
     else
        std::cout &lt;&lt; "fail" &lt;&lt; std::endl;
  }
  </code></pre>
  
  <p><strong>EDIT</strong>: to save you from having to run this code...</p>
  
  <ul>
  <li>If run as-is, it prints "fail" (undesireable, hard to debug).</li>
  <li>If you delete the line marked "oops" it prints "Foo" (desired behavior).</li>
  <li>If you leave the "oops" and make the two inheritances virtual, it won't compile (but at least you know what to fix).</li>
  <li>If you delete the "oops" and make them virtual, it will compile and will print "Foo"  (desired behavior).</li>
  </ul>
  
  <p>With virtual inheritance, the outcomes are either good or compiler-error.  Without virtual inheritance, the outcomes are either good or unexplained, hard-to-debug runtime failure.</p>
  
  <hr>
  
  <p>When I implemented Bar, which basically duplicated what Foo was already doing, it caused the dynamic cast to fail, which meant bad things in the real code.</p>
  
  <p>At first I was surprised there was no compiler error.  Then I realized there was no virtual inheritance, which would have triggered the 'no unique final overrider' error in GCC.  I purposefully chose not to use virtual inheritance since there aren't supposed to be any diamonds in this design.</p>
  
  <p>But had I used virtual inheritance when deriving from Base, the code would have worked just as well (without my oops), and I would have been warned about the diamond at compile time vs. having to track down the bug at run time.</p>
  
  <p>So the question is -- do you think it's acceptable to use virtual inheritance to prevent making a similar mistake in the future?  There's no good technical reason (that I can see) for using virtual inheritance here, since there should never be a diamond in the design.  It would only be there to enforce that design constraint.</p>