【问题标题】:calling a function from a friend function defined in a header in c++从 C++ 标头中定义的友元函数调用函数
【发布时间】:2010-10-30 23:55:03
【问题描述】:

我已将>> 运算符重新定义为标题中模板类中的友元函数。在其中,我需要调用另一个名为inputHelper 的函数,我也在标题中定义了该函数。 (输入助手是递归的)

头文件如下:

template< typename NODETYPE > class Forest
{
    /* (other friends) */
    friend void inputHelper(istream& file, int previousDepth,
        ForestNode<NODETYPE>& previousNode, ForestNode<NODETYPE> *nodeArray,
        int nodeCount)
    {
        /* (dostuff) */
        if(someconditional)
        {
            /* call inputHelper */
        }
    }

    friend istream& operator>>(istream& file, Forest<NODETYPE>& f1)
    {
        /* (dostuff) */
        /* (call inputHelper) */
    }
public:
    /* ... */
private:
    /* ... */
}

但是,在编译时,它显示|140|error: 'inputHelper' was not declared in this scope|。您是否必须做一些特别的事情,因为它们都被定义为标题中的友元函数?我有点理解inputHelper 超出了课程的范围,但我不确定如何解决这个问题。

【问题讨论】:

  • 请发布实际重现问题的代码(您发布的伪代码可能由于与您的问题无关的多种原因而无法编译)并告诉使用您究竟在哪里得到错误。 .

标签: c++ friend-function


【解决方案1】:

朋友函数不是成员函数。换句话说,它的范围超出了您的类的范围。通过将其声明为朋友,您将赋予它访问 Forest 类的受保护成员的特殊权限,但是您必须访问成员方法的方式应该使用该对象。 MememberMethod() 语法。

在这种情况下,您需要调用 f1.inputHelper(...),而不是直接调用 inputHelper(..)。如果你这样调用 inputHelper,我想它应该可以正常编译。

【讨论】:

    【解决方案2】:

    在您发布的代码中,您不是声明两个友元函数,而是声明 Forest 类的两个方法,因为您已将函数体写入类定义中。

    您应该让友元函数原型进入类,但在 Forest 类定义之外重写它们。

    【讨论】:

      【解决方案3】:

      您在这里混淆了两个概念:友元函数和成员函数。友元函数是在类定义之外定义的。类内部只有friend 声明,它只是声明在别处定义的某某非成员函数可以访问该类的私有成员。

      通过将inputHelper()operator&gt;&gt; 的主体连同它们的friend 声明一起包含在内,您已经使它们是成员函数还是朋友变得模棱两可了。此外,由于这些函数完全定义在类内部,因此它们不存在于类外部,这就是为什么当您尝试使用它们时编译器会给您一个错误。

      其实这更有趣。 operator&gt;&gt; 是一个成员函数,因为无论它是否是成员,使用它的语法都是相同的。但是,当您像非成员一样调用inputHelper() 时,编译器会给您一个错误。

      解决这个问题的方法是让编译器清楚谁是朋友,谁是成员。如果您希望 operator&gt;&gt;inputHelper() 成为友元函数,那么您只能将友元声明留在类中并放置它们的定义,即。 e.他们在课外的身体。

      
      template class Forest
      {
          /* (other friends) */
      
          friend void inputHelper(istream& file, int previousDepth,
              ForestNode& previousNode, ForestNode *nodeArray,
              int nodeCount); 
      
          friend istream& operator>>(istream& file, Forest& f1);
      public:
          /* ... */
      private:
          /* ... */
      };
      
      void inputHelper(istream& file, int previousDepth,
              ForestNode& previousNode, ForestNode *nodeArray,
              int nodeCount)
      {
              /* (dostuff) */
              if(someconditional)
              {
                  /* call inputHelper */
              }
      }
      
      istream& operator>>(istream& file, Forest& f1)
      {
              /* (dostuff) */
              /* (call inputHelper) */
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-08-11
        • 1970-01-01
        • 2013-02-16
        • 2018-12-05
        • 2018-11-06
        相关资源
        最近更新 更多