朋友模板功能的未定义参考

时间:2015-05-29 09:58:23

标签: c++

我正在尝试在普通类上实现朋友模板功能。

fren.h

#include <iostream>

namespace sn{


class Fren{
    private:
    int x;

    public:
    Fren(int y):x(y){

    }

template<typename B>
friend void getValue(B& asd);

};



template<typename B>
void getValue(B& asd);

}

fren.cpp

#include "fren.h"

namespace sn{

template<typename B>
void getValue(B& asd){
    std::cout<<asd.x<<std::endl;
}
}

的main.cpp

#include "fren.h"

int main() {

sn::Fren f(10);
sn::getValue(f);
return 0;
}

我想获得Fren的私人价值x。

但是我得到了“未定义的引用”错误。

1 个答案:

答案 0 :(得分:2)

首先,除非有其他原因,否则大多数属于单个头文件。有关原因,请参阅"Why can templates only be implemented in the header file?"

也就是说,如果要对函数模板使用显式实例化,则可以。请注意以下内容,这也比您的朋友更具限制性。此代码仅与具有匹配Fren的模板参数的函数模板相关联:

<强> func.h

#ifndef SAMPLE_FUNC_H
#define SAMPLE_FUNC_H

namespace sn
{

template<class T>
struct Fren;

template<class T>
void getValue(const Fren<T>& s);

template<class T>
struct Fren
{
    friend void getValue <>(const Fren<T>&);

    Fren() : x(42) {}

private:
    int x;
};

} // namespace


#endif

<强> func.cpp

#include "func.h"
#include <iostream>

namespace sn
{

template<class T>
void getValue(const Fren<T>& s)
{
    std::cout << s.x << ':' <<   __PRETTY_FUNCTION__ << '\n';
}

// explicit instantiation here
template void getValue <int> (const Fren<int>&);

}

<强>的main.cpp

#include <iostream>
#include <string>
#include "func.h"

int main()
{
    sn::Fren<int> s;
    sn::getValue(s);
}

<强>输出

42:void sn::func(const S<T> &) [T = int]

使用Apple LLVM版本6.1.0(clang-602.0.53)编译(基于LLVM 3.6.0svn)

简而言之,您的代码似乎缺少实际的显式实例化。