为什么不允许使用this的指针作为函数的默认参数

Why using a pointer of this as default parameter to a function not allowed?

本文关键字:函数 默认 参数 指针 this 为什么 不允许      更新时间:2023-10-16

我刚刚在二进制树中编写了一个有序函数,遇到了这个困难。

class BinaryTree
{
private:
     struct Node* o_root;
public:
BinaryTree()
    {
              o_root = new Node();    
        o_root->data = 0;
        o_root->left = NULL;
        o_root->right = NULL;
    }
    void inorder(Node*root = o_root);//Invalid
};

void BinaryTree::inorder(Node* root = o_root)//Invalid
    {
         if(root==NULL)
         {
             return;
         }
         inorder(root->left);
         cout<< root -> data;
         inorder(root->right);
    }

我得到一个错误:非静态成员引用必须相对于特定对象

如果我将根节点设置为静态,这是可行的。

为什么会这样?如果我有两个二叉树,我想要对象的特定根,而不是静态成员。我尝试使用this运算符,但这给了我另一个错误,基本上说在默认参数中不允许使用这个运算符。

有人能解释为什么这不起作用吗?为什么C++拒绝使用这个运算符作为默认参数?

这是因为当实际调用该方法时,this既没有定义,也不存在(想象得到的代码)。实际成员变量也是如此(如果没有指向数据的指针,也就无法访问数据)。

更详细地说,这也会导致没有真正定义的奇怪构造,比如下面(记住o_root甚至是私有的!):

sometree->inorder();
// ...would essentially be the same as...
sometree->inorder(sometree->o_root);

如何只是重载inorder(),删除默认参数?

基本上使用以下内容:

void BinaryTree::inorder(void)
{
    inorder(o_root);
}
void BinaryTree::inorder(Node* root)
{
    // your code as-is
}

实际上,您可以进一步缩小问题范围:

class A
{
   int x;
   void foo(int k = x);
};

这是因为标准是这么说的

您可以重载方法foo(),并在内部调用foo(x)

自8.3.6/9

[…]默认参数中不应使用非静态成员表达式,即使未对其求值,除非它显示为类成员访问表达式(5.2.5)的id表达式,或者除非用于形成指向成员(5.3.1)[…]的指针

为了深入了解,您可以阅读整个8.3.6