Метод «Contains» не работает так, как должен - PullRequest
1 голос
/ 28 февраля 2012

Я пытаюсь увидеть, если пользователь вводит какой-либо текст, он ищет в массиве какие-либо совпадения, а все, что не совпадает, удаляется из массива;

string search = textBox1.Text;
for (int i = 0; i < staffUsers.Count; i++)
{
    if (!(staffUsers[i].staff_name.Contains(search)))
    {
        staffUsers.Remove(staffUsers[i]);
    }
}

У меня есть несколько мусорных имен в моем массиве 'Rob Dob', 'Joe Bloggs', 'h h', 'ghg hgh', и если переменная поиска окажется 'R', Джо Блоггс будет удален, но ' hh 'и' ghg hgh 'остаются там, но там вообще нет R? любая причина, почему>?!

Ответы [ 6 ]

7 голосов
/ 28 февраля 2012

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

string search = textBox1.Text;

for (int i = staffUsers.Count - 1; i >= 0 ; i--)
{
    if (!(staffUsers[i].staff_name.Contains(search)))
    {
        staffUsers.Remove(staffUsers[i]);
    }
}
6 голосов
/ 28 февраля 2012

Проблема с вашим кодом заключается в том, что вы удаляете элементы, когда выполняете итерации по нему.Вы удаляете элемент, но продолжаете итерацию, даже если размер массива изменяется при удалении элемента.

Вам необходимо сбросить значение i после удаления чего-либо.В качестве альтернативы вам нужно использовать встроенный для выполнения тяжелой работы:

staffUsers.RemoveAll(i => !(i.staff_name.Contains(search))); 

Для выполнения работы используется крошечное выражение LINQ.Удалите все элементы, где этот предикат соответствует.i представляет элемент для применения выражения.Если это выражение имеет значение true, оно исчезает.

1 голос
/ 28 февраля 2012

Короче говоря, всякий раз, когда вы удаляете элемент с индексом [i], вы пропускаете элемент с индексом [i + 1]. Например, если ваш массив выглядит так:

{'Джо Блоггс', 'Роб Добб', 'h h', 'gafddf'}; я = 0

удалите Джо Блоггса, который находится в позиции 0.

{Роб Добб ',' h h ',' gafddf '}; = 1

удалить 'h h', который находится в позиции 1

{Роб Добб ',' gafddf '}; я = 2

i не меньше, чем yourArray.Count, поэтому цикл останавливается. Там нет позиции 2.

Самое быстрое решение - добавить i--, если вы удалите что-то из индекса [i]. В вашем случае

staffUsers.Remove(staffUsers[i]);
i--;

Надеюсь, это поможет!

0 голосов
/ 28 февраля 2012

Самый простой способ решить вышеуказанную проблему - использовать LINQ. Следующий код распутать над проблемой.

string search = textBox1.Text;
staffUsers= (from user in staffUsers
            where !user.Contains(search)
            select user).ToArray<string>();

Примечание: я предположил, что staffUsers - это массив строк.

0 голосов
/ 28 февраля 2012
string search = textBox1.Text;
for (int i = 0; i < staffUsers.Count; i++)
{
    if (!(staffUsers[i].staff_name.Contains(search)))
    {
        staffUsers.Remove(staffUsers[i]);
        // reset the index one stepback
        i--;
    }
}
0 голосов
/ 28 февраля 2012

В каждой итерации цикла либо удаляйте элемент, либо увеличивайте счетчик, а не обе операции. В противном случае вы пропустите следующий элемент массива при каждом удалении элемента массива:

string search = textBox1.Text;
for (int i = 0; i < staffUsers.Count;)
{
    if (!(staffUsers[i].staff_name.Contains(search)))
    {
        staffUsers.Remove(staffUsers[i]);
    }
    else
    {
        i++;
    }
}
...