错误的模板参数数量(3,应该是 4)

wrong number of template arguments (3, should be 4)

我尝试在 C++ 上使用 属性 来代替太多 setter 和数据中的 getter 函数 class 有很多成员变量。

有两个属性class。第一个固定了 setter 和 getter 函数默认设置,获取。第二个支持使用其 class 的自定义 setter 和 getter 函数。下面是代码

template <class T>
class Property
{
    T data;
public:
    // access with function call syntax
    Property() : data() { }
    T operator()() const
    {
        return data;
    }
    T operator()( T const & value)
    {
        data = value;
        return data;
    }
    // access with get()/set() syntax
    T get() const
    {
        return data;
    }
    T set( T const & value )
    {
        data = value;
        return data;
    }

    // access with '=' sign
    operator T() const
    {
        return data;
    }
    T operator = ( T const & value )
    {
        data = value;
        return data;
    }

    typedef T value_type; // might be useful for template deductions
};



// a read-write property which invokes user-defined functions
template <class T, class Object, T(Object::*real_getter)(), T(Object::*real_setter)(T const &) >
class RWProperty
{
    Object * my_object;
public:
    // this function must be called by the containing class, normally in a
    // constructor, to initialize the RWProperty so it knows where its
    // real implementation code can be found
    void operator () ( Object * obj )
    {
        my_object = obj;
    }

    // function call syntax
    T operator()() const
    {
        return (my_object->*real_getter)();
    }
    T operator()( T const & value )
    {
        return (my_object->*real_setter)( value );
    }

    // get/set syntax
    T get() const
    {
        return (my_object->*real_getter)();
    }
    T set( T const & value )
    {
        return (my_object->*real_setter)( value );
    }

    // access with '=' sign
    operator T() const
    {
        return (my_object->*real_getter)();
    }
    T operator = ( T const & value )
    {
        return (my_object->*real_setter)( value );
    }

    typedef T value_type; // might be useful for template deductions
};

我正在 OptionSet class 中测试这些属性,然后再将其放入项目代码

#include <QString>

class OptionSet
{
public:
    explicit OptionSet() {}

    Property<QString> m_MeshMode;

    RWProperty<uint, OptionSet, &getNumberOfVbo, &setNumberOfVbo> uNumberOfVbo; 
    // this causes problems

protected:

private:
    Property<uint> m_uNumberOfVbo;

    uint setNumberOfVbo(const uint& rVboCount)
    {
        // something to do here
        return m_uNumberOfVbo(rVboCount);
    }
    uint getNumberOfVbo() const
    {
        return m_uNumberOfVbo();
    }

};

但在使用 RWProperty 时,即使我传递了 4 个模板参数,如成员类型,class 类型具有 setter 和 getter 函数,getter 函数指针,setter函数指针顺序,它说

"wrong number of template arguments (3, should be 4) : RWProperty <uint, OptionSet, &getNumberOfVbo, &setNumberOfVbo> uNumberOfVbo"

"provided for 'template<class T, class Object, T(Object::*real_getter)(), T(Object::*real_setter)(const T&)> class RWProperty : class RWProperty"

我想我在模板中传递参数时做错了什么。

有没有人知道发生了什么事?

您的代码中存在三个错误:

首先,要获取成员函数的地址,需要包含class名称:

RWProperty<uint, OptionSet
         , &OptionSet::getNumberOfVbo
//         ~~~~~~~~~~~^
         , &OptionSet::setNumberOfVbo> uNumberOfVbo;
//         ~~~~~~~~~~~^               

其次,要形成指向const限定成员函数的指针,您需要在该指针的声明中附加const关键字:

T (Object::*real_getter)() const
//                         ~~~~^ to match 'uint getNumberOfVbo() const'

最后,OptionSet里面的OptionSet本身就是一个不完整的类型。除非该成员的声明点在前,否则您不能引用其成员。这基本上意味着您需要在 OptionSet 中重新排序您的声明,以便 setNumberOfVbogetNumberOfVbo 之前 您声明 uNumberOfVbo 数据成员:

class OptionSet
{
    //...

    uint setNumberOfVbo(const uint& rVboCount) { /*...*/ }
    uint getNumberOfVbo() const { /*...*/ }
    // Ok, now they are known and can be found in the class scope

    //...

    RWProperty<uint, OptionSet
            , &OptionSet::getNumberOfVbo
            , &OptionSet::setNumberOfVbo> uNumberOfVbo;
};