c ++:在完全定义类之前使用类作为模板参数

时间:2017-01-10 22:57:05

标签: c++ pointer-to-member

我很难理解为什么以下代码段会编译。我有一个模板类ptr_to_member<T>,它存储指向成员函数T的指针。然后我创建了一个新的my_classptr_to_member<my_class>。我预计后者会导致编译错误,因为my_class仍在定义中。任何帮助表示赞赏。谢谢。

#include <iostream>

// this class simply stores a pointer to a member function of T
template <class T>
struct ptr_to_member {

    using ptr_type = void (T::*)();
    ptr_type m_ptr;

    ptr_to_member()
    : m_ptr(&T::f){}

    auto get_ptr() const {
        return m_ptr;
    }
};

// my_class has a ptr_to_member<my_class>
class my_class {

    ptr_to_member<my_class> m_ptr_to_member; // why does this compile?

public:

    void g() {
        auto ptr = m_ptr_to_member.get_ptr();
        (this->*ptr)();
    }

    void f() {
        std::cout << "f" << std::endl;
    }
};

int main() {

    my_class x;
    x.g();

}

1 个答案:

答案 0 :(得分:0)

在定义类时,可以使用该类,就像它是向前声明的一样。由于ptr_to_member仅使用指向T的指针,直到您实例化其中一种方法,因此它不会抱怨。尝试添加成员T而不是指针,您将看到它失败。直观的看待方式是,您不需要知道T使用T的指针是什么,只有T是一种类型。无论指向什么指针,指针的行为方式都相同,直到你取消引用它们为止。

template <class T>
struct ptr_to_member {

    using ptr_type = void (T::*)();
    ptr_type m_ptr;

    ptr_to_member()
        : m_ptr(&T::f) {}

    auto get_ptr() const {
        return m_ptr;
    }

    T member; // Add this and see that it fails to compile
};

有关何时可以使用前向声明类型的详细信息,请参阅this answer