在一个for循环中遍历vector,如果vector的某一项被clear后,如何保证能遍历完整的vector

在C++中遍历vector时,删除或清空元素可能导致迭代器失效。为确保完整遍历,可以使用临时迭代器或索引。通过临时迭代器,当删除元素后更新迭代器;使用索引则标记待删除元素,后续统一处理。文章提供了四种不同情况下的示例代码来说明这一方法。
摘要由CSDN通过智能技术生成

在遍历vector时,如果在循环中删除或清空了其中的某个元素,可能会导致迭代器失效或者遍历不完整。为了确保遍历整个vector,可以考虑使用迭代器或者索引来遍历。

如果使用迭代器,可以在循环中使用一个临时的迭代器保存要删除的元素的下一个迭代器,然后在循环体中使用这个临时迭代器来遍历vector。这样可以确保即使有元素被删除,也能继续遍历整个vector。示例代码如下:

std::vector<int> vec = {1, 2, 3, 4, 5};
for (auto it = vec.begin(); it != vec.end(); ) {
    if (*it == 3) {
        auto temp = it; // 保存要删除的元素的下一个迭代器
        ++temp;
        vec.erase(it); // 删除元素
        it = temp; // 更新迭代器
    } else {
        std::cout << *it << " ";
        ++it;
    }
}

如果使用索引,可以在循环中使用一个计数器来记录当前遍历到的索引位置,然后在删除元素时不直接删除,而是将要删除的元素的值置为一个特殊的标记(如-1),最后再遍历一次vector,将所有标记的元素删除。这样可以确保即使有元素被删除,也能继续遍历整个vector。示例代码如下:

std::vector<int> vec = {1, 2, 3, 4, 5};
int count = 0;
for (auto& elem : vec) {
    if (elem == 3) {
        elem = -1; // 标记要删除的元素
    } else {
        std::cout << elem << " ";
    }
    ++count;
}
for (int i = 0; i < count; ++i) {
    if (vec[i] == -1) {
        vec.erase(vec.begin() + i); // 删除标记的元素
        --i;
        --count;
    }
}
#include <iostream>
#include <vector>

using namespace std;

int main() {
    vector<string> v = {"hello", "world", "!", "how", "are", "you"};

    for (auto it = v.begin(); it != v.end(); ) {
        if (it->empty()) {
            it = v.erase(it);
        } else {
            cout << *it << " ";
            ++it;
        }
    }

    return 0;
}
#include <iostream>
#include <vector>

using namespace std;

int main() {
    vector<string> v = {"apple", "banana", "cherry", "durian", "eggfruit", "fig"};

    for (auto it = v.begin(); it != v.end(); ) {
        if (distance(v.begin(), it) == 2) {  // 判断是否为第三项
            it = v.erase(it);  // 删除第三项
        } else {
            if (!it->empty()) {  // 判断元素是否为空
                cout << *it << " ";  // 输出非第三项且非空的元素
            }
            ++it;
        }
    }

    return 0;
}
#include <iostream>
#include <vector>

using namespace std;

int main() {
    vector<string> v = {"apple", "banana", "cherry", "durian", "eggfruit", "fig"};

    for (auto it = v.begin(); it != v.end(); ) {
        int idx = distance(v.begin(), it);
        if (idx == 2 || idx == 4) {  // 判断是否为第三项或第五项
            it = v.erase(it);  // 删除第三项或第五项
        } else {
            if (!it->empty()) {  // 判断元素是否为空
                cout << *it << " ";  // 输出非第三项、第五项且非空的元素
            }
            ++it;
        }
    }

    return 0;
}
#include <iostream>
#include <vector>

using namespace std;

int main() {
    vector<string> v = {"apple", "banana", "cherry", "durian", "eggfruit", "fig"};

    vector<int> indices_to_remove = {2, 4};  // 需要移除的索引列表

    sort(indices_to_remove.begin(), indices_to_remove.end());  // 将需要移除的索引列表按照升序排序

    int removed_count = 0;  // 记录已经移除的元素个数

    for (auto it = v.begin(); it != v.end(); ) {
        int idx = distance(v.begin(), it);
        if (removed_count < indices_to_remove.size() && idx == indices_to_remove[removed_count]) {  // 判断是否需要移除当前元素
            it = v.erase(it);  // 删除当前元素
            ++removed_count;  // 更新已经移除的元素个数
        } else {
            if (!it->empty()) {  // 判断元素是否为空
                cout << *it << " ";  // 输出非移除项且非空的元素
            }
            ++it;
        }
    }

    return 0;
}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

时间简史u

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值