簡體   English   中英

在C ++中,為什么不能使用另一個類的模板類型來管理模板類成員函數?

[英]In C++, why isn't it possible to friend a template class member function using the template type of another class?

換句話說,為什么編譯正常:

template<typename Type>
class A{
  public:
    void f();
};

class B{
  friend void A<int>::f();
};

template<>
void A<int>::f(){
  B* var = new B();
}

雖然這不是:

template<typename Type>
class A{
  public:
    void f();
};

template<typename Type> // B is now a templated class
class B{
  friend void A<Type>::f(); // Friending is done using B templated type
};

template<>
void A<int>::f(){
  B<int>* var = new B<int>(); // var is now declared using int as its templated type
}

對於第二個代碼片段,編譯器(gcc 6.2,沒有特殊標志)說:

main.cpp: In instantiation of ‘class B<int>’:
main.cpp:14:28:   required from here
main.cpp:9:15: error: prototype for ‘void A<int>::f()’ does not match any in class ‘A<int>’
   friend void A<Type>::f();
               ^~~~~~~
main.cpp:13:6: error: candidate is: void A<Type>::f() [with Type = int]
 void A<int>::f(){

據我所知,在第二個代碼片段中,當聲明var時,編譯器應該解析B類聲明,用int替換友元聲明中使用的Type,一切都應該正常工作。 我錯過了什么?

編輯:下面的評論指出,第二個代碼片段似乎與clang和Visual C ++ 2015正確編譯

A<int>::f()使用B<int>之前的顯式實例化可以解決此問題。 我假設GCC在A<int>::f()的定義中嘗試隱式實例化B<int> 但是A<int>::f()的定義沒有完成,GCC'丟失'了朋友聲明。 它看起來像編譯器問題。

template<typename Type>
class A
{
public:
    void f();
};

template<typename Type> // B is now a templated class
class B
{
    friend void A<Type>::f(); // Friending is done using B templated type
};

template
class B<int>; // <= explicit instantiation, that works

template<>
void A<int>::f()
{
    B<int>* var = new B<int>();
}

專業template class成員函數沒有專門的整個template class是特殊情況,當你被允許專門化非template成員函數,所以也許GCC很困惑,我不知道原因,但不知何故你不能聲明友誼到專業template classtemplate成員。 臨時解決方案是專門為整個class template工作。

//class template A
template<typename Type>
class A{
  public:
    void f();
};

//class A<int>
template<>
class A<int>{
  public:
    void f();
};

然后,定義A<int>::f

對於class B:

void A<int>::f(){
      B* var = new B();
      (void)(var);
}

對於template class B

void A<int>::f(){
      B<int>* var = new B<int>();
      (void)(var);
}

但我認為Clang就在這里,對於這樣的朋友宣言應該沒有問題。 這可能是GCC的一個錯誤。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM