5.2.1. 基本構成: フロントエンドとバックエンド

以下に簡単なコード例を示す。

例 5.5. フロントエンドとバックエンド

template <typename T, typename U>
class backend
{
  // ...
};

template <typename T>
struct frontend
{
  template <typename U>
  struct bind { typedef backend<T, U> type; };
};

void foo()
{
  typedef int T;
  typedef std::string U;
  typedef frontend<T>::template bind<U>::type A;
}

クラステンプレートbackendは、クライアントコードに提供されるクラステンプレートの本体である。これをバックエンドと呼ぶ。このクラステンプレート自体には2相テンプレートのトリックは含まれていない。

クラステンプレートfrontendは、2相テンプレートのトリックのためだけに存在するクラステンプレートである。これをフロントエンドと呼ぶ。フロントエンドは唯一のメンバbindを持つ。bindはクラステンプレートであり、その内部に同じく唯一のメンバtypeを持つ。bindtypeは、クライアントコードに提供するクラステンプレートの本体を実体化する際に使用される。

クライアントコードfoo内の別名Aの定義のうち、第1テンプレートパラメータTまでを実体化したものがfrontend<T>であり、第2テンプレートパラメータUまでを実体化したものがfrontend<T>::template bind<U>::typeである。結果として、frontend<T>::template bind<U>::typebackend<T, U>の別名になる。

上記の例では、フロントエンドに1パラメータを、フロントエンドからバックエンドを導出する際に1パラメータを取るが、パラメータの個数はそれぞれ任意である。0でもよい。