Спринты на стадионе

тема: Префиксные суммы · уровень: средний

Условие

На школьном стадионе тренер записал результаты спринтов по дням. Иногда он спрашивает: «А сколько в этом отрезке дней были *по-настоящему быстрыми* — строго быстрее заданного порога?»

Ваша задача — быстро отвечать на такие вопросы.

Формат ввода

В первой строке два целых числа n и q — число дней и число вопросов. Во второй строке n целых чисел a1, a2, ..., an — результат в каждый день. Далее идут q строк, в каждой три целых числа l r t.

Это означает: посчитать, сколько значений ai на позициях l..r строго больше t.

Формат вывода

Выведите q строк. В i-й строке — ответ на i-й вопрос.

Ограничения

Пример

Ввод:

5 3
2 5 1 4 3
1 5 3
2 4 1
3 3 0

Вывод:

2
2
1

Как решать — идея подхода

Приём: Оффлайн-обработка + дерево Фенвика (BIT)

Ключевое наблюдение: запрос «сколько ai на l..r строго больше t» — это про порог. Если рассматривать t от большого к маленькому, то множество индексов с ai > t только растёт: при уменьшении t добавляются новые дни.

Приём: оффлайн-обработка (сначала читаем все запросы, потом отвечаем) + дерево Фенвика (BIT) для быстрых подсчётов количества отмеченных индексов на отрезке. BIT хранит 1 в позиции i, если день уже «достаточно быстрый», иначе 0. Тогда ответ — сумма на отрезке.

План:

Сложность: сортировки O((n+q) log(n+q)), обновления и запросы BIT — O((n+q) log n).

Частая ошибка: перепутать строгость — нужно именно ai > t, а не >=. Ещё следи за 1-индексацией в BIT и формулой sum(r) - sum(l-1).

Разберись руками

Есть 5 дней со значениями: 2 5 1 4 3. Вопрос спрашивает: на отрезке дней l..r сколько значений строго больше порога t. Попробуем руками на примере увидеть, как отвечать без пересчёта каждого отрезка заново.

Идея: Для каждого вопроса можно мысленно заменить каждый день на 0 или 1 (подходит ли он под «строго больше порога»). Потом один раз слева направо посчитать накопленные итоги. Тогда количество подходящих дней на любом отрезке находится как разность: сколько накопилось к правому концу минус сколько было накоплено до начала отрезка.

Решить задачу с автопроверкой на Python →

Куда дальше