title: C++ friend comparison between two instantiations of one class template
body: <p>I am trying to write a class template that provides a comparison operator between two instatiations with different template types. As is often the case, this operator is a non-member friend. A simplified example of what I am trying to achieve can be seen below.</p>
  
  <pre><code>template&lt;typename T&gt;
  class Wrapper {
    // Base type, which must have a val() method to allow comparison
    T t_;
  public:
    Wrapper(const T&amp; t) : t_(t) {}
  
    // Comparison operator
    template&lt;typename B&gt;
    friend
    bool
    operator==(const Wrapper &amp;a, const Wrapper&lt;B&gt;&amp;b) {
      return a.t_.val()==b.t_.val();
    }
  };
  
  // First example type for Wrapper
  class X {
    int x_;    
  public:
    X(int x) : x_(x) {}
  
    int
    val() const {return x_;}
  };
  
  // Second example type for Wrapper
  class Y {
    int y_;
  public:
    Y(int y) : y_(y) {}
  
    int
    val() const {return 2*y_;}
  };
  
  int
  main() {
    Wrapper&lt;X&gt; WX(X(4));
    Wrapper&lt;Y&gt; WY(Y(2));
    return WX==WY ? 1 : 0;
  }
  </code></pre>
  
  <p>This example (g++ 4.4.0) doesn't compile: instead it complains that <code>y_</code> from <code>Wrapper&lt;Y&gt;</code> is private and so inaccessible to the friend function, and I can see why. But how can I fix this? Adding friendship to the reversed function</p>
  
  <pre><code>  template&lt;typename B&gt;
    friend bool operator==(const Wrapper&lt;B&gt; &amp;, const Wrapper &amp;);
  </code></pre>
  
  <p>into the Wrapper class template body merely causes ambiguity to the compiler. I don't want to allow different instatiations of the Wrapper class to have access to the private members of each other - I want to restrict access to this one operator. Is this possible? </p>
  
  <p>My laptop's in peril from being defenestrated, so any ideas would be appeciated by both me and the laptop (and the window for that matter).</p>