必须将类方法中的新指针转换为引用

时间:2017-09-14 10:46:22

标签: c++ pointers reference

我有两个课程,我们称之为A和B

class A:
{
  public:
    //Some functions

    A *getNewA() const;

  private:
    //some attributes
}

class B:
{
  public:
    //Some functions
  private:
    A &reftoA;
}

在主代码中,由于A :: getNewA()方法,我 必须 生成一个新的A.这个必须转到B :: reftoA,如B类所示。

这是A :: getNewA()方法:

A *A::getNewA()
{
    A *newA = new A;
    return newA;
}

行。所以现在我调用getNewA并希望将结果存储在reftoA中,这是一个引用到A.在B函数中(以A作为参数引用)

B::foo(A &paramA)
{
    reftoA = *(paramA.getNewA());
}

我认为这应该是有效的,但它不会。 因为在解除引用时,reftoA将始终采用此对象而不是新分配的对象。

让我们更清楚,让我们修改功能以输出结果

A * A::getNewA()
{
    A *newA = new A;
    std::cout << "New pointer " << newA << std::endl;
    std::cout << "this pointer" << this << std::endl;

    return A;
}

void B::foo(A &paramA)
{

    reftoA = *(paramA.getNewA());
    std::cout << "new generated pointer " << &reftoA << std::endl;
}

以下是输出之一:

New pointer : 004FFAEC
this pointer: 0069D888
New generated pointer : 0069D888 //Expected : 004FFAEC

我无法得到这个&#34;新生成的指针&#34;与分配内存后A :: getNewA()返回的新指针相同。当然,我想有一点是解除引用指针将其存储在引用中。 我知道引用与现有对象一起使用。也许新对象A :: getNewA()应该按照我的预期为你的工作分配内存。

我可以在B :: foo()中使用指针代替引用,我知道,但 我不能

我认为我误解了关于参考和指针的事情,但我不知道是什么。

任何帮助非常感谢

3 个答案:

答案 0 :(得分:4)

问题是您无法重新分配参考。您只能更改引用对象的值。

因此,您必须在B类构造函数的初始化列表中初始化引用。

请注意您的代码段中存在拼写错误

A*A::getNewA()
{
A *newA = new A;
std::cout << "New pointer " << newA << std::endl;
std::cout << "this pointer" << this << std::endl;

return A;
^^^^^^^^^ 
}

我认为你的意思是

A*A::getNewA() const
               ^^^^^
{
A *newA = new A;
std::cout << "New pointer " << newA << std::endl;
std::cout << "this pointer" << this << std::endl;

return newA;
^^^^^^^^^^^ 
}

始终尝试提供可验证的完整示例。

这是一个示范程序

#include <iostream>

class A
{
public :
    //Some functions

    A* getNewA() const
    {
        A *newA = new A;
        std::cout << "New pointer " << newA << std::endl;
        std::cout << "this pointer" << this << std::endl;

    return newA;
    }

private :
    //some attributes
};

class B
{
public :
    B( const A& a ) : reftoA( *a.getNewA() )
    {
        std::cout << "&reftoA " << &reftoA << std::endl;
    }
private :
    A& reftoA;
};

int main() 
{
    A a;

    B b( a );

    return 0;
}

它的输出是

New pointer 0x2b392afbec20
this pointer0x7ffd287ad0af
&reftoA 0x2b392afbec20

正如您所看到的,New pointer&reftoA的值彼此相等。

为了更清楚地考虑一个非常简单的例子

#include <iostream>

int main() 
{
    int x = 10;
    int y = 20;

    int &r = x;

    r = y;

    std::cout << "x = " << x << std::endl;
    std::cout << "y = " << y << std::endl;
    std::cout << "r = " << r << std::endl;

    std::cout << std::endl;

    std::cout << "&x = " << &x << std::endl;
    std::cout << "&y = " << &y << std::endl;
    std::cout << "&r = " << &r << std::endl;

    return 0;
}

程序输出

x = 20
y = 20
r = 20

&x = 0x7ffd88ad47a8
&y = 0x7ffd88ad47ac
&r = 0x7ffd88ad47a8

本声明

    r = y;

没有强制引用引用对象y。它只是重新分配了引用对象x的值。

引用必须在创建时初始化。

答案 1 :(得分:1)

是的,你误解了一些事情。

getNewA()正在返回一个指针。它不是一个聪明的指针,你想看看那些,这就是我在这件事上所说的。

在返回指针时,你必须保持对这个指针的引用,否则你将无法删除它,你将得到内存泄漏。因此,你必须在某个地方A* a = A::getNewA()然后,当你不再需要它时delete a;

如果你需要传递对A的引用,你可以执行foo(*a),它将取消引用指针并传递对它所指向的对象的引用。

但总的来说,对于所有新代码,智能指针;没有理由不使用它们。

旁注:您的代码示例还有其他一些问题;比如getNewA不是静态的;我将把代码作为你理解的工作实例,而不是一个有效的例子。

编辑:在重新阅读您的示例时,getNewA是故意非静态的。我认为这个问题实际上是一个XY问题(即你问的问题是你强迫自己进入但不是你的实际问题);但我希望这可以解决你对指针和参考文献的误解。

答案 2 :(得分:0)

您没有在getNewA - 方法

中返回指针
A* A::getNewA()
{
    A *newA = new A;
    return A; // you are returning A and not newA
}

如果您想将引用重新分配给a,可以使用std::reference_wrapper

class B :
{
public :
void foo(A& paramA) {
    reftoA = *(paramA.getNewA());
}

private :
std::reference_wrapper<A> reftoA;
}