将 PRIVATE 嵌套(内部)class 的非成员函数定义放在哪里?

Where to put non-member function definition of a PRIVATE nested (inner)class?

以下是我的实际问题的一个简单示例。我有一个使用定义的非成员函数 friend 中的关键字 InnerClass。这个函数的定义应该在InnerClass.

之外

另一方面,class 定义在 MyClassprivate 下,因为我想使用 InnerClass 专门用于 MyClass

在这种情况下,我实际上可以在哪里放置 friend 函数的定义?

#include <iostream>

class MyClass
{
private:
    class InnerClass
    {
        int m_int;
    public:
        InnerClass(int i) :m_int(i) {}

        // non-member (friend) function, for which I need a definition outside the class!
        friend std::ostream& operator<<(std::ostream& output, const InnerClass &obj);
    };
    // ERROR: too many parameter for this operator
    std::ostream& operator<<(std::ostream& output, const InnerClass &obj)
    {
        return output << obj.m_int << " ";
    }

private:
    InnerClass m_innerClass;

public:
    explicit MyClass(int i) : m_innerClass{ i } {}
    friend std::ostream& operator<<(std::ostream& output, const MyClass &obj);
};

std::ostream& operator<<(std::ostream& output, const MyClass &obj)
{
    output << obj.m_innerClass << std::endl;
}


int main()
{
    MyClass classObj{ 2 };
    std::cout << classObj;
    return 0;
}

错误消息:

  \main.cpp(27): error C2804: binary 'operator <<' has too many parameters
  \main.cpp(27): error C2333: 'MyClass::operator <<': error in function declaration; skipping function body

您实际上可以在 class 定义中定义友元非成员函数。

这是您修复的代码片段:

#include <iostream>

class MyClass
{
private:
    class InnerClass
    {
        int m_int;
    public:
        InnerClass(int i) :m_int(i) {}

        // non-member (friend) function, which we can define right here
        friend std::ostream& operator<<(std::ostream& output, const InnerClass &obj)
        {
            return output << obj.m_int << " ";
        }
    };    

private:
    InnerClass m_innerClass;

public:
    explicit MyClass(int i) : m_innerClass{ i } {}
    friend std::ostream& operator<<(std::ostream& output, const MyClass &obj);
};

std::ostream& operator<<(std::ostream& output, const MyClass &obj)
{
   return output << obj.m_innerClass << std::endl;
}


int main()
{
    MyClass classObj{ 2 };
    std::cout << classObj;
    return 0;
}

你可以对另一个 operator<< 做同样的事情。

现在,如果 InnerClass 不是私有的,您仍然可以在全局范围内定义该函数,但您需要完全限定第二个参数的名称:

std::ostream& operator<<(std::ostream& output, const MyClass::InnerClass &obj)
{                                                //  ^^^^^^^^^^^^^^^^^^^ 
    return output << obj.m_int << " ";
}