用于c ++中的循环迭代

时间:2011-04-01 04:00:57

标签: c++ arrays

我正在使用C ++中动态分配的数组构建一个简单的列表。我有一个函数remove(int item),它应该删除列表中出现的所有item。但是,如果我在数组中创建一个从0迭代到length的循环,我担心我会超出数组的边界,因为length在删除项目时会发生变化:< / p>

int List::pop(int index)
{
  int retval = data[index];
  for (int i = index; i < length; i++)
    data[i] = data[i+1];
  length--;
  return retval;
}

void List::remove(int item)
{
  for (int i = 0; i < length; i++) {
    if (data[i] == item)
      pop(i);
}

因此,如果我在remove(6)上调用了array[6][4][2][6][1][3][5][6],那么C ++会在for之后使用remove()的更新值更新length循环pop() 1}?或者它会在调用remove()时保持与最初传递给它的值相同吗?

3 个答案:

答案 0 :(得分:3)

另一种解决方案是反向搜索。只保留那些与项目不相同的项目。

void List::remove(int item)
{
    int insert = 0;
    for (int i = 0; i < length; i++) {
        if (data[i] != item)
          data[insert++] = data[i];
    }
    length = insert;
}

答案 1 :(得分:2)

从数组末尾开始,然后向后返回起始位置。或者,请致电pop(i--)而不是pop(i)。这会备份i,因此您不会跳过列表中的任何元素(包括最后一项)。

第一种方法的优点是你不会浪费时间向下移动最终会被移除的元素。

答案 2 :(得分:2)

在循环的每次迭代之前,完整地计算条件表达式i < length。 C ++编译器不会缓存i,也不会缓存length进行此评估。只要length变量被正确更新,这个表达式就不允许i超出数组的范围。

但这对跳过元素问题没有帮助。要做到这一点,我会切换到while循环。

int i = 0;
while (i < length) {
  if (data[i] == item) {
    pop(i);
  } else {
    i++;
  }
}

在这种情况下,如果我们pop项目,我们不会增加。这样,索引保持在同一个位置,并且能够捕获在数组中彼此相邻的重复项