【问题标题】:C++ delete pointer to dynamic allocated objectC++删除指向动态分配对象的指针
【发布时间】:2017-11-27 10:08:05
【问题描述】:

我加载一个文本文件,然后从它的数据中创建动态分配的对象,然后将它们的指针存储在一个向量中,并根据每个对象类型将它存储在另外两个容器之一中,我有两个问题: 首先:如果我在读取文件函数中声明并初始化对象,然后添加指向向量的指针,在我删除它之前,这个对象在函数之外是否可用?如果没有,解决方案是什么? 第二:我使用下面的函数来释放内存:

for (int it = 0; it < phongItems.size(); it++) {
    delete phongItems[it];
    phongItems[it] = nullptr;
}

所以我从包含所有对象的主容器中删除对象,我是否必须对具有相同指针的其他容器执行此操作?

注意:我在这一点上不是很强大,所以如果有误解,请清除它并希望减少反对票。

编辑:

我使用以下方法加载文本文件,我迭代它的行然后每行应该创建一个必须添加到向量中以供以后使用的项目:

void Game::loadLevel(std::string file) {
    initAssets(mgr, dataPath, file);
    std::string line;
    ifstream f(dataPath + file);
    if (!f.is_open())
        LOGE("game error while opening file %s", file.c_str());
    while (getline(f, line)) {
        std::vector<std::string> tokens;
        sSplit(line, ' ', tokens);
        if (tokens[0] == "MESH") {
            std::vector<std::string> typeToken;
            sSplit(tokens[2], '=', typeToken);
            std::vector<std::string> nameToken;
            sSplit(tokens[1], '=', nameToken);
            std::vector<std::string> countToken;
            sSplit(tokens[3], '=', countToken);
            std::vector<std::string> matrixToken;
            sSplit(tokens[4], '=', matrixToken);
            int count = atoi(countToken[1].c_str());
            //if I declare the pointer here and added it to the vector I can't use it later
            StaticItem* item;
            std::vector<GLfloat> mToken;
            fSplit(matrixToken[1], ',', mToken);
            item = new StaticItem(*engine, "/models/" + nameToken[1] + ".obj",nullptr,0);
            item->narrow = true;
            engine->addItem(item, true, true);              
        }
    }
    if (f.bad())
        LOGE("game error while reading file %s", file.c_str());
    f.close();
}

void Engine::addItem(EngineItem* item, bool collision, bool loader) {
    if (collision)
        collisionItems.push_back(item);
    if (loader)
        loadItems.push_back(item);
    phongItems.push_back(item);
}

如果我使用智能指针或原始指针,函数完成后指针将超出范围,这是什么想法?

【问题讨论】:

  • 您应该只通过new 致电delete 一次。并且使用智能指针或适当的容器应该可以避免自己使用任何new(所以不要使用delete)。
  • @Jarod42 我在将它们声明为类成员之前使用shared_ptr,现在我必须从文本文件创建对象,所以我不知道它包含什么,直到我阅读它,如果我在 load 函数中声明 shared_ptr 并将其添加到容器中,我猜它会超出函数结束的范围并变得不可用,我会收到错误
  • 您可以从您的加载功能转移所有权。 (没有代码,很难给你纠正你的错误)。
  • 1.只要对象未被删除或超出范围,它们就可用。 2. 正如@Jarod42 指出的,删除应该只执行一次。
  • @Jarod42 我添加了代码

标签: c++ pointers dynamic-allocation


【解决方案1】:

一个问题很多,但我会尽力解释。

如果我在读取文件函数中声明并初始化对象 然后添加指向向量的指针,这个对象是否可用 在函数之外,直到我删除它?

是的,如果对象是在堆上创建的(使用新的),它将可以从提到的向量中获得。

所以我从包含所有对象的主容器中删除对象,我是否必须对具有相同指针的其他容器执行此操作?

删除或取消引用(使用)已经删除的指针是错误的,你应该只从向量中删除指针,以防止它被进一步使用。

如果我使用智能指针或原始指针,指针将不在 函数完成后的作用域,那么思路是什么?

如果你会使用智能指针,这取决于。在向量中存储非智能指针是没有用的,因为对象将在您指向时被删除。所以你应该把共享指针放在向量中,在这种情况下对象不会被删除,直到任何共享指针存在。

总而言之,我敢打赌,使用共享指针是最好的解决方案。 Crate 共享指针,把它放在你需要的任何向量中。当您要删除对象时,只需从任何向量中删除共享对象,对象将被自动删除。

【讨论】:

  • 谢谢你,这回答了我所有的问题,现在的愿景很清晰。
猜你喜欢
  • 2012-11-06
  • 1970-01-01
  • 2016-03-02
  • 2011-05-02
  • 2021-03-29
  • 1970-01-01
  • 1970-01-01
  • 2013-09-09
  • 1970-01-01
相关资源
最近更新 更多