当对象仍在范围内时,Arduino类析构函数被调用

问题描述 投票:1回答:2

我正在为ESP8266开发一个小类,我需要能够在同一个对象的另一个实例中保存对象的引用。运行代码时,我一直在获取异常。经过一些调试后,它看起来像是在对象仍在范围内时调用类析构函数。我很长时间没有使用过C ++,但这种行为似乎不对。

真的有两个问题。

  1. 当对象仍在范围内时,为什么要调用析构函数?
  2. 是否可以在没有调用析构函数的情况下保持对象超出对象范围的引用(如在链表中)?

我已经将代码缩减为一个显示问题的小程序。在下面的代码中,类'析构函数在'child'对象上调用,而它仍在范围内。我在代码中指出它实际上被调用了两次。

这是代码的输出:

        Starting
        adding child to root
        Out of scope name=child
        adding child to root2
        Out of scope name=child
        Done, both root and child should still be in scope
#include "Arduino.h"

class TestObject {
    private:
       char name[20];
       TestObject* child;

    public:
       TestObject(const char* name);
       virtual ~TestObject();
       void setChild(TestObject h) ;
       char *getName();
};

TestObject::TestObject(const char *name) {
    child = (TestObject*)0;
    strcpy(this->name,name);
}

TestObject::~TestObject() {
    Serial.println("Out of scope name="+String(name));
}

char *TestObject::getName() {
    return name;
}

void TestObject::setChild(TestObject h ) {
    child = &h;
    Serial.println("adding "+String(h.name)+" to "+String(name));
}

void setup() {
  Serial.begin(115200);
  delay(1000);
  Serial.println("\nStarting");
  TestObject root = TestObject("root");
  TestObject child = TestObject("child");
  root.setChild(child); // child destructor is called here but it should still be in scope
  delay(1000);
  TestObject root2 = TestObject("root2");
  root2.setChild(child);// child destructor is called a second time here
  Serial.println("Done, both root and child should still be in scope");
  while(true) {
    delay(10000);
  }
}
c++ arduino destructor esp8266
2个回答
3
投票

TestObject::setChild按值获取其参数,以便创建TestObject的副本,由函数使用,然后销毁。这是你所看到的析构函数的来源。 setChild也指向这个本地副本,因此child中的TestObject指针指的是一个被破坏的对象。

解决方案是通过引用传递参数:

void TestObject::setChild(TestObject &h)

0
投票

在void setChild(TestObject h)中;您将成员的子指针设置为临时(参数)的地址。您可能想要传递引用void setChild(TestObject&h);但即便如此,子指针也无法延长对象的生命周期。

© www.soinside.com 2019 - 2024. All rights reserved.