【问题标题】:Deleting a pointer from a vector using loops (not iterators)使用循环(不是迭代器)从向量中删除指针
【发布时间】:2018-12-30 02:51:55
【问题描述】:

我有一个方法,它传递一个对象,通过在循环中匹配其地址在指针向量中找到该对象,并且需要从向量中删除匹配项而不删除该项(即该项需要仍然存在于内存中)。目前是这样的方法:

void remove(Soldier& soldier) {
    for (size_t i = 0; i < armySize(); ++i) {
        if (army[i] == &soldier) {
            cout << army[i]->getName() << "is removed" << endl;
            army.erase(i);
            break;
        }
    }
}

其中soldier 是需要移除的对象,armySoldier 指针的向量。 if 语句有效,这意味着soldier 的地址和向量中的一个项目匹配。问题是我收到一条错误消息,提示“没有匹配的成员函数调用'erase'”。如果不使用迭代器(没有 new、delete 或 begin 方法),我将如何解决这个问题?

【问题讨论】:

  • 为什么不想使用迭代器?
  • army.begin() + i 是您要删除的项目的迭代器。不知道你为什么对这么简单的事情死心塌地。
  • 我不能使用迭代器,因为这是规范的一部分

标签: c++ c++11 computer-science


【解决方案1】:

您可以将要擦除的元素与最后一个交换元素并使用std::vector::pop_back()

 if( i != army.size() - 1 ) 
     std::swap( army[i], army.back() );
 army.pop_back();

在你的情况下,如果你使用指针,你可以简单地覆盖:

army[i] = army.back();
army.pop_back();

此方法比调用std::vector::erase() 更有效,但会影响元素的顺序。

【讨论】:

    【解决方案2】:

    如果你看一下std::vector::erase的声明,它是:

    iterator erase( const_iterator pos );
    

    如您所见,参数是一个交互器。您正在尝试将整数作为参数传递。因此,重载决议不会找到您传递的参数类型的重载。这就是错误 "no matching member function for call to 'erase'" 的意思。

    不使用迭代器就无法使用std::vector::erase


    如何在不使用迭代器的情况下解决此问题

    您可以用最后一个元素覆盖要删除的元素,然后调用pop_back 删除重复项。这两个都可以在没有迭代器的情况下完成。

    如果你想像erase 那样保持顺序,那么用下一个覆盖目标元素。然后用之后的覆盖下一个,依此类推,直到向量结束。然后pop_back。也就是说,我建议使用迭代器和erase。没有必要通过任意禁止使用迭代器来使程序复杂化。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-10-06
      • 2019-10-05
      • 2014-03-23
      • 1970-01-01
      相关资源
      最近更新 更多