我在哪里可以找到关于“int C :: *”用法的描述?

时间:2011-07-31 15:23:20

标签: c++ stl

在一段代码中,我找到了一些东西:

template<typename T>
class IsClassT {
  private:
    typedef char One;
    template<typename C> static One test(int C::*);
...

问题是我在哪里可以找到关于为什么“int C :: *”的使用在函数test()定义中有效的描述?

3 个答案:

答案 0 :(得分:10)

int C::*是指向C类型int成员的指针。搜索“指向成员的指针”。处理此声明语法的标准部分(ISO / IEC 14882:2003)是8.3.3指向成员的指针[dcl.mptr]。

使用示例。

struct Example
{
    int a;
    int b;
};

int test( Example& ex, int Example::* p )
{
    return ex.*p;
}

int main()
{
    Example x = { 3, 5 };
    // Convoluted way of extracting x.a and x.b
    int a = test( x, &Example::a );
    int b = test( x, &Example::b );
}

答案 1 :(得分:6)

我不会描述int C::*的含义,因为@Charles Bailey已经做得很好。不过我会回答你的问题:

  

(...)为什么“int C :: *”的用法在函数test()中有效   定义

关键点是int C::*(指向int类型成员的指针)的使用是有效的当且仅当 C是类类型时。否则,int C::*类型格式不正确。

这就是你

的原因
template<typename C> static One test(int C::*);

并且很可能在某处

template <typename> static Two test(...);
static const bool value = sizeof(test<T>(0)) == 1;

当编译器看到test<T>(0)时,它会检查test的候选者。它找到两个:

template<typename C> static One test(int C::*);   
template <typename> static Two test(...);

第一个优先于第二个,因为1)它们都是模板函数,2)最后查找省略号。如果第一个形成不良(即当且仅当 C不是类类型),那么它只是被丢弃而第二个重载是拍摄。此行为的昵称为 SFINAE (替换失败不是错误)。

测试返回类型的大小(记住sizeof(char)始终为1),您可以在编译时评估test采取的内容,即。 T是否为班级类型。

答案 2 :(得分:2)

这是指向成员的指针 一个简单的例子来理解成员指针

class A
{
   int a;
   int b;
   void DoSomething();
};

int main()
{
   A *ObjPtr;

   //pointer to member a
   int A::*ptr = &A::a;    

   //Usage
   objPtr->*ptr = NULL;

   //pointer to member function
   void (A::*FuncPtr)(void) = &A::DoSomething; 

   //Usage
   (objPtr->*FuncPtr)(void);    

   return 0;
}