继承的成员函数似乎未声明,发生了什么?

时间:2016-11-24 21:30:12

标签: c++ templates inheritance

我想编译一个C ++软件,它给了我一些编译 错误。此错误是关于无法解析的成员函数。

这个问题应该包含回答所需的一切。但是,如果那样 真的是这样,我现在应该找到答案了。所以请随意 浏览source code。 此问题中的所有代码都不是我的,而是根据GPLv2许可。

我编译的系统是运行Red Hat Enterprise Server的IBM PowerPC 740 6.8。使用模块,我启用了Clang 3.7。一切都得到了交叉编译 对于IBM PowerPC A2芯片,它是IBM BlueGene / Q超级计算机。那些事 应该由我的compilation script照顾 这设置了所需的许多configureCXXFLAGS

我目前使用当前状态获取的编译错误(提交 fee0a02)就是这个:

bfmcommqmp.C:183:5: error: use of undeclared identifier 'gather'
    gather(result_cb, psi, dag);
    ^

违规行在bfmcommqmp.C中的此方法定义中:

168 template <class Float>                                                          
169 void bfmcommQMP<Float>::comm_start(int result_cb, Fermion_t psi, int dag) {     
170     // gather the faces. Routines here are threaded.                            
171     // All threads cooperate in gathering.                                      
172                                                                                 
173     //  if ( this->isBoss() && (me == 0)) {                                     
174     //    this->Error("comm_start checking heap\n"); fflush(stdout);            
175     //    mcheck_check_all();                                                   
176     //    this->Error("comm_start mcheck_all");fflush(stdout);                  
177     //  }                                                                       
178                                                                                 
179     int me = this->thread_barrier();                                            
180                                                                                 
181     this->thread_barrier();                                                     
182                                                                                 
183     gather(result_cb, psi, dag);                                                
184                                                                                 
185     this->thread_barrier();                                                     
186     if (me == 0) {                                                              
187         comm_qmp_start(psi);                                                    
188     }                                                                           
189     this->thread_barrier();                                                     
190                                                                                 
191     return;                                                                     
192 }

这当然是bfmcommQMP课程的一部分。看着相关的 头文件bfmcommqmp.h,找到这个类声明:

  8 template <class Float>                                                          
  9 class bfmcommQMP : public bfmbase<Float> {                                      
 10   public:                                                                       
 11     // QMP thingy-me-bob's                                                      
 12     QMP_msghandle_t multi_handle[2];                                            
 13                                                                                 
 14     QMP_msgmem_t send_ops_msgmem_t[8];                                          
 15     QMP_msgmem_t recv_ops_msgmem_t[8];                                          
 16                                                                                 
 17     QMP_msghandle_t send_multi_handle;                                          
 18     QMP_msghandle_t send_handles[8];                                            
 19                                                                                 
 20     QMP_msghandle_t recv_handles[8];                                            
 21     QMP_msghandle_t all_handles;                                                
 22                                                                                 
 23     Float *simd_rbuf[8];                                                        
 24     Float *receive_area;                                                        
 25                                                                                 
 26     int num_op;                                                                 
 27                                                                                 
 28     virtual bool isBoss();                                                      
 29                                                                                 
 30     virtual void recv_init(void);                                               
 31     virtual void recv_end(void);                                                
 32                                                                                 
 33     virtual void comm_init(void);                                               
 34     virtual void comm_end(void);                                                
 35     virtual void comm(int result_cb, Fermion_t psi, int dag);                   
 36     virtual void comm_start(int result_cb, Fermion_t psi, int dag);             
 37     virtual void comm_qmp_start(Fermion_t psi);                                 
 38     virtual void comm_qmp_complete(void);                                       
 39     virtual void comm_merge(void);                                              
 40     virtual void comm_complete(int result_cb, Fermion_t psi);                   
 41     virtual void comm_gsum(double &val);                                        
 42     virtual void comm_gsum(double *val, int N);                                 
 43 };

它继承自bfmbase。跳转到包含在其中的文件bfm.h bfmcommqmp.h,我们找到了类定义,其中包含两个gather 方法:

 133 template <class Float>                                                          
 134 class bfmbase : public bfmarg, public ThreadModel {                             
 135   public:  

 282     void gather(int result_cb, Fermion_t psi, int dag);
 283     void gather(int mu, int result_cb, Fermion_t psi, int dag); 

1018 };

根据我的理解,班级bfmcommQMP应该继承了。{ 来自gather的非虚拟函数bfmbase。显然情况并非如此, 否则Clang不会抱怨。

我在这里缺少什么?为什么函数gather在函数内部不可用 bfmcommQMP::comm_start会员功能?

1 个答案:

答案 0 :(得分:2)

问题是您的派生类是dependent name。您需要使用gather()限定基类中对this->gather()的调用,否则编译器不会从基类解析gather()。为了简化,

template<class T> struct Base
{
    void f();
};

template<class T> struct Derived: Base<T> // dependent name
{
    void foo()
    {
        this->f(); // won't compile without this->
    }
};

另一种方法是

using Base::f;
派生Derived::foo()中的

或限定呼叫,如

Base::f();

相关:Why do I have to access template base class members through the this pointer?