Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/142.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/templates/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 模板类的某些友元函数显示未定义的引用_C++_Templates_Friend_Friend Function - Fatal编程技术网

C++ 模板类的某些友元函数显示未定义的引用

C++ 模板类的某些友元函数显示未定义的引用,c++,templates,friend,friend-function,C++,Templates,Friend,Friend Function,最初正在处理其他人先前提出的一个问题:。看到OP没有完全利用DataOut和GetData的模板,所以我也尝试将它们作为模板 以下是我最终得到的代码: #包括 #包括 模板 类数组{ 公众: tu[10]; 友元无效数据输出(常量数组&); friend void GetData(数组&); }; 模板 无效数据输出(常量数组和arr){ 标准::cout>arr.U[0]; std::cin.clear(); } int main(){ 阵列Arr1; Getdata(Arr1); 数据输出(

最初正在处理其他人先前提出的一个问题:。看到OP没有完全利用
DataOut
GetData
的模板,所以我也尝试将它们作为模板

以下是我最终得到的代码:

#包括
#包括
模板
类数组{
公众:
tu[10];
友元无效数据输出(常量数组&);
friend void GetData(数组&);
};
模板
无效数据输出(常量数组和arr){
标准::cout>arr.U[0];
std::cin.clear();
}
int main(){
阵列Arr1;
Getdata(Arr1);
数据输出(Arr1);
}
但是,我得到了对
DataOut
的未定义引用:
main.cpp:(.text+0x3a):对'DataOut(Array const&')的未定义引用。

我找到了两种方法来解决这个问题:

  • 数组
    类中定义
    数据输出
  • 在main中调用
    DataOut
    ,而不仅仅是
    DataOut

  • 问题是,为什么
    GetData
    没有发生错误?我还尝试按不同的顺序调用和定义它们,但结果仍然相同

    有什么我遗漏的吗?或者是我的编译器(
    clang7.0.0
    )的错误?

    您声明了两个(系列)非模板友元函数

    template<class T>
    class Array{
    public:
        T U[10];
    
        friend void DataOut(const Array&);
        friend void GetData(Array&);
    };
    
    例如,如果您将在main中添加以下语句

    f( A<long>() );
    
    f(A());
    
    然后编译器将发出错误,因为没有这样的非模板函数。类模板的这种专门化的函数没有定义

    您可以在类中定义friend非模板函数。在这种情况下,编译器将为类模板的每个专门化实例化所谓的模板化实体

    这就是函数模板声明

    template<class T>
    void DataOut(const Array<T>& arr){
        std::cout << arr.U[0];
    }
    
    模板
    无效数据输出(常量数组和arr){
    
    std::coutVlad回答了我的大部分问题。同时,我从一些gcc警告中找到了如何将friend函数定义为模板函数:

    template<class T>
    class Array;         // Forward declaration of the Array<T> class
    
    template<class T>
    void DataOut(const Array<T>& arr){
        std::cout << arr.U[0];
    }
    
    template<class T>
    class Array{
    public:
        T U[10];
    
        friend void DataOut<>(const Array<T>&);    // `<>` used right after `DataOut`
    }
    
    模板
    class Array;//数组类的前向声明
    模板
    无效数据输出(常量数组和arr){
    
    std::cout@Ranoiaetep您是否看到GetData和GetData是两个不同的名称?也就是说,您输入了一个错误,并声明了两个具有不同名称的函数。请注意,这使friend成为一个模板。在OP中,它不是。这可能会导致一些行为更改。
    template<class T>
    void DataOut(const Array<T>& arr){
        std::cout << arr.U[0];
    }
    
    template<class T>
    class Array;         // Forward declaration of the Array<T> class
    
    template<class T>
    void DataOut(const Array<T>& arr){
        std::cout << arr.U[0];
    }
    
    template<class T>
    class Array{
    public:
        T U[10];
    
        friend void DataOut<>(const Array<T>&);    // `<>` used right after `DataOut`
    }