Skip to content
2009/05/11 / highmt

クラステンプレートのテンプレート引数をフレンドにできるか

VS2003で次のようなC++コードが通っていたのだけれど、
VS2008では通らなくなった。

template < class T >
class X
{
  friend class T;
};

VS2008では、次のようにすると通る。

template < class T >
class X
{
  friend T;
};

g++4.3.3では、どうも駄目らしい。

error: a class-key must be used when declaring a friend

ISO/IEC 14882:2003では

A friend of a class or class template can be a function template or class template, a specialization of a function
template or class template, or an ordinary (nontemplate) function or class.

ということで、template-parameterはだめなような感じがする。

よくよく考えれば、どうコンパイルしてよいかよくわからないコードではあるのだけれど、
(クラステンプレートのインスタンス化がどこかにあればprivateアクセスを許す?
違う翻訳単位にインスタンス化があったらどうするんだろう。)
もともと、Xにポリシークラスを渡して、ポリシークラスではXのprivateメンバを触れるけど
X自体を使う側はXの公開インタフェースを通して使うようにする、という意図でこのようなコードを書いていた。

どうやら、ポリシークラスもXの公開インタフェースを通すか、
ポリシークラス用にインタフェースを分けたければ、
きちんと、ポリシークラスへの公開用にXのラッパーを用意してこれをfriendにし、
ポリシークラスは直接Xに触らずにこのラッパー経由でアクセスさせるべきのよう。

—————-

2009/05/21 06:11
http://d.hatena.ne.jp/faith_and_brave/20081201/1228122639
friend class T の形は C++03では不適格との記述が。

7.1.5.3 2 If the identifier resolves to a typedef-name or a template type-parameter, the elaborated-type-specifier is ill-formed.
[Note: this implies that, within a class template with a template type-parameter T, the declaration
  friend class T
is ill-formed.]

本当だ。

VC9 の friend T は C++0xの先取りなのか。

広告
%d人のブロガーが「いいね」をつけました。