模板化代理设计模式

时间:2018-02-04 13:13:22

标签: c++ templates declaration forward-declaration

我有一个简单且可重现的代码,看起来像这样:

template <typename T>
class Proxy {
private:
    Wrap<T> &self; // If I comment this, it will work
public:
    Proxy() {}
};

template <typename T>
class Wrap {
    T *p;
public:
    Proxy<T> foo() {
        return Proxy<T>();
    }
};

int main()
{
    return 0;
}

我得到的错误是:

  

&#39;环绕&#39;没有命名类型

如果我评论Wrap<T> &self,那么它会起作用,但这不是我需要的。我需要Wrap<T>成为Proxy班级的成员。我怎样才能做到这一点?

2 个答案:

答案 0 :(得分:5)

您可以在Wrap的类定义之前添加forward declaration Proxy,否则编译器无法知道它是类模板的名称。值得注意的是,引用数据成员不需要类型为complete type,因此前向声明就足够了。

// forward declaration
template <typename T>
class Wrap;

template <typename T>
class Proxy {
private:
    Wrap<T> &self;
public:
    Proxy() {}
};

顺便说一下,以下问题是参考数据成员self未初始化。

LIVE of Clang

  

错误:'Proxy'的构造函数必须显式初始化引用成员'self'

答案 1 :(得分:4)

您需要添加前向声明:

template<class T> class Wrap;

template <typename T>
class Proxy {
private:
    Wrap<T> &self;
public:
    Proxy() {}
};

template <typename T>
class Wrap {
    T *p;
public:
    Proxy<T> foo() {
        return Proxy<T>();
    }
};

int main()
{
    return 0;
}

代码只是从OP的问题中复制而来。但是你仍然需要关注会员Wrap<T> &self。作为参考,它应该在构造函数中初始化。