Why am I getting a Linker error with template function pointer?

筅森魡賤 提交于 2019-12-02 07:10:47

If you simply declared the template in a .h file and the implementation is instead in a .cpp file then this is the error you will get, because a C++ compiler works one compile unit at a time. When the compiler finds your code calling a template function that has been just declared it will assume that the concrete instantiation will be done by some other compilation unit (there is no way the compiler can know where to find the .cpp file for that function... the compiler only sees one .cpp and all the included .h at a time).

If the template parameters are from a well known list you can simply request the all explicit implementations you know that will be needed for the program in the .cpp.

For example if you have a template function

template<typename T>
T foo(T x)
{
   ...
}

and you know are just going to need int foo(int); and string foo(string); then it's fine to use just the declaration in the .h, provided you also add two lines in the .cpp saying:

template<> int foo(int);
template<> string foo(string);

By doing that you are telling the compiler about what specialization to build. If you later end up using other specializations (e.g. vector<int> foo(vector<int>)) then you must also add this explicit instantiation in the .cpp file of the template.

However in your example looking at the code I guess that you don't know in advance which kind of events will be defined and so this explicit instantiation cannot be done.

The other solution is to simply put the whole template implementation in the .h file instead of separating declaration from implementation. This sometimes can be not trivial because requires you to expose more implementation details probably introducing more dependencies.

This probably means that RegisterListener is not actually implemented anywhere. As it is a template function, you should implement it in the header.

Try the following in the header.

template< class T, class EvenT > 
void RegisterListener(T* listener, int EventType, void (T::MemFunc)(EvenT) ) { }
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!