Алгоритмы count_if и find_if
Алгоритмы count и find
Использование алгоритмов
2500 400 17 5 1
P.pop();
P.push(2500); P.push(1);
P.push(17); P.push(5); P.push(400);
while (!P.empty()) {
cout << P.front() << ' ';
}
return 0;
}
Результат выполнения программы:
Вернемся к изучению алгоритмов. Не забывайте включать заголовочный файл <algor1thm> и добавлять определение нашей функции print (), если она используется.
Алгоритм count подсчитывает количество вхождений в контейнер (или его часть) значения, заданного его третьим аргументом.
Алгоритм find выполняет поиск заданного значения и возвращает итератор на самое первое вхождение этого значения.
Если значение не найдено, то возвращается итератор, соответствующий возврату метода end(). В следующей программе показано использование этих алгоритмов.
int main() {
int arr[ ] = {1, 2, 3, 4, 5, 2, 6, 2, 7};
int n = sizeof(arr) / sizeof(int);
vector<int> v1(arr, arr + n);
int value = 2 ; // искомая величина
int how_much = count (vl.begin(), vl.end(), value);
cout << how_much << endl; // вывод: 3
list<int> loc_list; // список позиций искомой величины
vector<int>: :iterator location = v1.begin();
while (1) {
location = find (location, v1.end(), value);
if (location == v1.end()) break;
loc_list.push_back(location – v1.begin());
location++;
}
print(loc_list); // вывод: 1 5 7
return 0;
}
В приведенной программе создается вектор v1, наполняясь при инициализации значениями из массива arr.
Затем с помощью алгоритма count подсчитывается количество вхождений в вектор значения value, равного двум.
В цикле while выясняется, на каких позициях в векторе размещена эта величина.
Обратите внимание на то, что первый аргумент алгоритма find (переменная location) первоначально — перед входом в цикл — принимает значение итератора, указывающего на нулевой элемент контейнера.
Затем location получает значение итератора, указывающего на найденный элемент.
Если поиск завершился успешно, то, во-первых, вычисляется позиция найденного элемента как разность значений location и адреса нулевого элемента.
Полученное значение заносится в список loc_list .
Во-вторых, итератор location сдвигается операцией инкремента па следующую позицию в контейнере, чтобы обеспечить (на следующей итерации цикла) продолжение поиска в оставшейся части контейнера.
Если поиск завершился неудачей, то break приведет к выходу
из цикла.
Алгоритмы count_if и find_if отличаются от алгоритмов count и find тем, что в качестве третьего аргумента они требуют некоторый предикат.
Предикат — это функция, возвращающая значение типа bool.
Например, если в предыдущей программе добавить определение глобальной функции:
bool isMyValue (int х) { return ((х > 2) && (х < 5)); }
и заменить инструкцию с вызовом count на:
int how_much = count_if (v1.begin(), v1.endO, isMyValue);
то программа определит, что контейнер содержит два числа, значение которых больше двух, но меньше пяти.
Аналогично, замена инструкции с вызовом find на
location = find_if (location, v1.end() , isMyValue);
будет иметь следствием наполнение списка loc_list двумя значениями: 2 и 3 (номера позиций вектора v1, на которых находятся числа, удовлетворяющие предикату isMyValue).