在QT中,我试图设置自己的Qwidget,以便由于内存管理和其他内容,一切都应该很好地工作。但是,我似乎无法通过指针,堆和堆栈才能得到一切。我的小部件mywidget具有带有一些对象的Qlist。我不知道如何正确设置所有内容。

您可以在下面看到我的代码,我对此有一些疑问:

  1. 即时变量列表是在堆上创建的,最好在堆栈上创建它吗?

  2. 在我的列表中,我有指针,最好只在堆栈上创建对象并将其附加到列表中吗? (这样我根本没有指针)

  3. 当我将对象附加到列表中时,他们会自动将列表作为父母自动获取吗?因此,当我删除列表时,列表中的所有对象将被删除?

  4. 我要使用的每个循环不起作用,我得到了“预期该操作的指针/数组类型,而不是'int'”

  5. 在我的代码中,我想创建其他将对象从列表中作为参数获取的小部件。这是正确的方法吗? Myotherwidget的实例方法看起来像:myotherwidget(myObject *myObject,qwidget *parent)

谢谢你的帮助!我是QT和C ++的新手,所以如果您可以指导我朝正确的方向引导我,那就太好了。如何以正确的方式设置此设置,以使其变得简单,不要获得内存泄漏并根据需要使用尽可能少的内存。您将如何设置同一件事?

这是我的代码:

mywidget.h:

class MyWidget : public QWidget
{
Q_OBJECT

public:
    MyWidget(QWidget *parent = 0);
    ~MyWidget();

private:
    QList<MyObject*> *list;
};

mywidget.cpp:

MyWidget::MyWidget(QWidget *parent)
{
    ui.setupUi(this);

    list = new QList<MyObject*>();
    for (int i = 0; i<10; i++) 
    {
        MyObject *myObject = new MyObject("Hello",this);
        list->append(myObject);
    }

    foreach(MyObject *myObject, list)
    {
        //Lets say I want to create other widgets here and that they takes a MyObject as a parameter
        MyOtherWidget *myOtherWidget = new MyOtherWidget(myObject,this);
    }

}

MyWidget::~MyWidget(){
    delete list;
}
有帮助吗?

解决方案

AD.1。列表的寿命应与MyWidget实例的寿命相同,因此您可以在堆栈上安全地创建列表。

AD.2。您可以做到这一点,但是MyObject类需要具有默认构造函数,复制构造函数和一个分配运算符(请参阅 http://doc.trolltech.com/4.6/containers.html#container-classes 有关详细信息)。

AD.3。对象的所有权未在附加内容上转移。就像STL容器一样,QT容器不会在存储的指针上调用DELETE。要删除存储在Qlist(或其他QT容器)中的所有指针,您可以使用QDeleteAll(列表)。请注意,您可能不想在发布的代码中这样做:您将myWidget指针传递给myObject构造函数,我认为它然后用作qobject parent。因此,当MyWidget删除时,所有QOBjects都将被删除。

AD.4。 foreach宏的第二个论点应该是一个容器,而不是指针到容器。因此,如果您的列表变量是Qlist的指针,则应致电foreach(myObject *obj, *list)。

AD.5。只要MyotherWidget不删除传递的MyObject(因为MyWidget已经是MyObject的父,并且您最终将同一对象删除同一对象)。

这是一个简单的简化,但是您应该尝试以完全不需要调用DELETE的方式编写代码。在堆栈上创建东西或依靠QT父母机制(即父母删除孩子)。稍后,您可能需要阅读有关智能指针(QSHAREDPOINTER,QSCOPEDPOINTER等)的信息。

编辑:

MyObject的父级设置是否取决于您在MyObject构造函数中所做的事情。如果您将父级参数传递给qobject构造函数,即您的myObject构造函数看起来像这样:

MyObject(const QString &text, QObject *parent = 0) : QObject(parent)
{
// more code...
}

将设置父,因为它将在qobject构造器中完成,该代码将被称为“:qObject(parent)”代码。如果您没有这个碎片怎么办?由于MyObject继承了qObject,并且您不指定哪个构造函数应称为默认的qObject构造函数,即qobject(qObject *parent *parent = 0),因此您的myObject的父级将是null的,并且不会为删除。

我会尽量避免通过setparent方法明确设置父 - 对于基本用例,在构造函数中设置parent应该足够。

尝试使用正确的术语(不是“实例方法”,而是“构造函数”),读取QT文档,使用常识,并尽量不要以为会自动完成任何操作。父母不是仅仅因为您调用一个参数“ parent”的“自动”设置 - 它是设置的,因为有一块代码在qobject构造函数中执行此操作,并且您有责任将适当的parth pass pass pass pass pass pasth parth to Chonstort在类中继承Qobject。

其他提示

是的,问题在于您要删除列表的对象,而不是其元素!

我建议您看看:

QList<Employee *> list;
list.append(new Employee("Blackpool", "Stephen"));
list.append(new Employee("Twist", "Oliver"));

qDeleteAll(list.begin(), list.end());
list.clear();

更多信息在这里

我还会问您是否真的需要指向列表的指针?您可以简单地简单:

QList<MyObject*> list;

因此,您的内存泄漏较少!

希望这个对你有帮助 !

编辑 :
3.您的MyObject对象作为父母具有“此”。当您处理指针时,该列表不会占用对象。
4.对于循环,也许您应该考虑迭代器,在这里看看 qthelp://com.trolltech.qt.460/qdoc/qlist.html.

只要您使它们成为当前小部件的父母,您就无需将儿童小部件存储在列表中。 (通常,您可以在堆栈上使用New创建小部件)。

QT具有自动清洁函数,这意味着,如果删除了小部件,则所有子小部件(父母是被删除的小部件的小部件)被删除。

因此,您唯一必须确保(尤其是对于临时弹出窗口小部件)删除/删除小部件“弹出窗口”或调用弹出窗口小部件的唯一一件事。

就是这样。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top