Jump to content
  • Advertisement
Sign in to follow this  
kohma

[C++] no contextual type information in my code, need help

This topic is 3844 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hi, I'm programming a lua-to-c++ library, but more for myself and fun. In it I work a lot with partial template specializations and non-type template arguments. Right now I get an error msg like "test.cpp:51: error: address of overloaded function with no contextual type information". Maybe somebody could help me on unterstanding why the code fails. At the end you find a copy&compileable stripped down version of my code. I would really appreciate any help or ideas :)
#include <iostream>
#include <vector>

using namespace std;
typedef vector<int> vec;
typedef vec::reference tref;
typedef vec::size_type tsize;

template<typename T, T* P>
struct FunWrapper {
};

template<typename T, T P>
struct MemFunWrapper {
};

template<typename tRet,typename A1,tRet (*func)(A1)>
struct FunWrapper<tRet(A1),func> {
  static void foo() { cout<<"Fun Wrap"<<endl; }
};

template<class C,typename tRet,typename A1,tRet (C::*memFunc)(A1)>
struct MemFunWrapper<tRet(C::*)(A1),memFunc>{
  static void foo() { cout<<"Mem Fun Wrap"<<endl; }
};

template<typename T,T* P>
void reg() {
  FunWrapper<T,P>::foo();
}

template<typename T,T P>
void reg() {
  MemFunWrapper<T,P>::foo();
}

template<typename T,T P>
void reg_mf() {
  MemFunWrapper<T,P>::foo();
}

int main() {
  /* on gcc 4.1.1 the following line gives me                                                                                                                      
     test.cpp:51: error: address of overloaded function with no contextual type information                                                                        
                                                                                                                                                                   
     if you comment out the FunWrapper<tRet(A1),func> specialization it works as well                                                                              
  */
  //reg<tref(vec::*)(tsize),&vec::at>();                                                                                                                           

  /* this version works */
  reg_mf<tref(vec::*)(tsize),&vec::at>();
  return 0;
}

Share this post


Link to post
Share on other sites
Advertisement
vec::at() is actually two different functions const int & vec::at(size_type) const and int & vec::at(size_type). What the error message is telling you is that it can't figure out which one you mean. You can disambiguate it with a cast.

Share this post


Link to post
Share on other sites
Sorry, but I don't understand what you mean.

Even though I know it wouldn't work I tried:
 reg<tref(vec::*)(tsize),static_cast<tref(vec::*)(tsize)>(vec::at)>(); 


One cannot cast something in the template parameter list. More specifically my compiler complains "a cast to a type other than an integral or enumeration type cannot appear in a constant-expression".

But this wasn't probably what you meant by casting. Also it's weird that if I comment the one specialization out (see the source), the compiler doesn't complain. Even though the specialization wasn't for member function pointers but for normal function pointers.

Could you please be a little bit more verbose?

Share this post


Link to post
Share on other sites
I've redone my example code and I narrowed down the problem. Probably I get some more responses now :)


/* takes function type as first template parameter */
/* and a function pointer of the function type as */
/* the second template parameter */
template<typename T,T* P>
void reg() { }

/* takes member function type as first template */
/* parameter and member function pointer of the type */
/* as second template parameter */
template<typename T,T P>
void reg() { }

template<typename T,T P>
void reg_mf() { }

struct T_at_atconst {
int at(int) { }
const int at(int) const { }
};

int main() {
/* the compiler only can't cope with the normal and */
/* the const version of the member function */
/* if there are two versions of the template function */
/* one which accepts function pointers and one which */
/* accepts member function pointers */
/* but actually the memFun type should be clear since */
/* I have to give as the first template parameter */

/* so this works and the compiler can deduce which */
/* version of the member function should be used */
reg_mf<int(T_at_atconst::*)(int),&T_at_atconst::at>();
reg_mf<const int(T_at_atconst::*)(int)const,&T_at_atconst::at>();

/* but this won't work, why? */
//reg<int(T_at_atconst::*)(int),&T_at_atconst::at>();
//reg<const int(T_at_atconst::*)(int)const,&T_at_atconst::at>();

return 0;
}



I cannot explain this odd behaviour. Maybe somebody can explain. Maybe it's explained in the standard or it's just a flaw of my compiler.

Thanks in advance :)

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!