Ошибка сегментации C ++ при итерации по вектору

У меня есть программа, которая поддерживает целочисленный вектор. У меня есть три функции, которые добавляют целое число, удаляют целое число и проверяют, есть ли целое число уже в векторе. Проблема с последним.

vector<int> children;
void CtpTestingApplication::addChild(int child)
{
for (int i=0; i<children.size(); i++)
{
//already a child
if (children[i]==child)
return;
}
//child not yet recorded
children.push_back(child);
cout<<"added child "<<child;
}

void CtpTestingApplication::removeChild(int child)
{
for (int i=0; i<children.size(); i++)
{
//already a child, remove it
if (children[i]==child)
{
children.erase(children.begin()+i);
cout<<"removed child "<<child;
}
}
//not recorded, no need to remove
}

bool CtpTestingApplication::isChild(int child)
{
vector<int>::iterator ic;
bool result = false;
for (ic= children.begin(); ic < children.end(); ic++)
{
cout<<*ic<<" vs "<<child;
//     if (child==*ic)
result = true;
}
return result;
}

Я всегда получаю ошибку сегментации, когда я раскомментирую «if (child == * ic)», даже если распечатки показывают, что вектор не пустой и содержит ожидаемые целые числа.

Например, с комментариями if я вижу
1 против 4,
2 против 4,
4 против 4,
12 против 4

Я также пытался зацикливаться с использованием children [i] и так далее, но безрезультатно. Любая помощь будет оценена. Спасибо.

1

Решение

Ваш цикл должен измениться с этого:

   for (ic= children.begin(); ic < children.end(); ic++)

к этому:

  for (ic= children.begin(); ic != children.end(); ic++)

Это не решит проблему, поскольку используемый контейнер является вектором, и для этого класса контейнера определена разница между итераторами векторов. Тем не менее, это все еще хорошая практика, чтобы предпочитать,

ic != container.end()

потому что это будет работать для контейнеров, которые не имеют этого определения.

2

Другие решения

Как указал Джон 3136, единственная потенциальная проблема, которую я вижу, связана с removeChild функция. Попробуйте переписать это так:

void CtpTestingApplication::removeChild(int child)
{
int i=0;
while (i<children.size())
{
if (children[i]==child) {
children.erase(children.begin()+i);
continue;
}
i++;
}
}

Почему вы получаете Сегфо, можно только догадываться. Одна возможность состоит в том, что removeChild() может вызываться в каком-то другом потоке, делая недействительным ваш итератор в isChild(), Это будет возможно только в том случае, если вы используете потоки без надлежащего мьютексирования (в этом случае у вас гораздо большая проблема 🙂

1

По вопросам рекламы [email protected]