РУҚА
Задания № 17, 24, 25 · ЕГЭ

Запросы к массиву

Как быстро отвечать на запросы о суммах и количествах элементов массива
6 мин чтенияСложность: Обновлено 29 сентября 2026

Запрос к массиву — это вопрос о его элементах: найти сумму или количество на отрезке, определить среднее, максимум, минимум или число элементов, удовлетворяющих условию. Главный приём темы — заранее построить вспомогательный массив префиксных значений, чтобы каждый запрос обрабатывался за \(O(1)\), а не перебирал все элементы заново.

Модель запроса и индексы

Пусть дан массив \(a_1,a_2,\ldots,a_n\). Запрос обычно задаёт отрезок индексов от \(l\) до \(r\), причём оба конца включаются. Например, запрос «найти сумму элементов с 3-го по 7-й» означает \(a_3+a_4+a_5+a_6+a_7\). В программировании индексы могут начинаться с нуля, поэтому важно заранее решить, какую нумерацию использует условие и код.

D
Запрос на отрезке

Запрос на отрезке \([l;r]\) — это вычисление характеристики элементов \(a_l,a_{l+1},\ldots,a_r\). Длина отрезка равна \(r-l+1\), потому что оба конца входят в отрезок.

\[\operatorname{len}(l,r)=r-l+1\]1

Если запросов немного, каждый можно обработать обычным циклом. Но при большом числе запросов такой способ медленный: один длинный отрезок требует до \(n\) операций. Для сумм и количеств применяют кумулятивную сумму, которую также называют префиксной суммой.

Префиксная сумма и сумма на отрезке

Префиксная сумма \(p_i\) — сумма первых \(i\) элементов массива. Удобно добавить нулевой элемент \(p_0=0\). Тогда \(p_i\) содержит сумму \(a_1+a_2+\ldots+a_i\).

D
Префиксная сумма

Префиксная сумма массива — это массив \(p\), в котором \(p_i\) равна сумме элементов от начала массива до позиции \(i\). Она строится последовательно: к предыдущей сумме прибавляется очередной элемент.

\[p_0=0,\qquad p_i=p_{i-1}+a_i\quad (1\le i\le n)\]2

Сумму на отрезке \([l;r]\) получаем вычитанием: из суммы первых \(r\) элементов убираем сумму первых \(l-1\) элементов. Это и есть основной ответ для суммы на отрезке.

\[S(l,r)=a_l+a_{l+1}+\ldots+a_r=p_r-p_{l-1}\]3
T
Правило двух префиксов

После построения массива \(p\) любой запрос суммы на отрезке отвечает за \(O(1)\): достаточно выполнить одно вычитание \(p_r-p_{l-1}\). Предварительное построение занимает \(O(n)\).

a₁a₂a₃a₄a₅отрезок [2;4]
Сумма на отрезке [2;4] равна \(p_4-p_1\).

Количество элементов на отрезке

Чтобы быстро считать элементы, удовлетворяющие условию, строят не сумму самих значений, а сумму индикаторов. Для каждого элемента задаём \(b_i=1\), если условие выполнено, и \(b_i=0\) в противном случае. Префиксные суммы массива \(b\) дают количество подходящих элементов на любом отрезке.

\[b_i=\begin{cases}1,&\text{если }a_i\text{ удовлетворяет условию},\\0,&\text{иначе},\end{cases}\qquad C(l,r)=q_r-q_{l-1}\]4

Например, для подсчёта чётных элементов условие \(a_i\bmod 2=0\). Для подсчёта положительных элементов — \(a_i>0\). Такой подход связан с условным счётчиком, но префиксный массив позволяет отвечать на запросы сразу для разных отрезков.

№
Разобранный пример: сумма и количество

Дан массив \(a=[4,-2,7,0,5,3]\). Нужно ответить на запросы: сумма элементов \([2;5]\) и количество положительных элементов на \([1;4]\).

1
Добавим нулевой элемент и построим префиксные суммы исходного массива.
p=[0,4,2,9,9,14,17]
2
Для суммы от 2 до 5 вычтем сумму первых \(1\) элемента из суммы первых \(5\).
\(\displaystyle S(2,5)=p_5-p_1=14-4=10\)
3
Создадим индикаторы положительности: единица означает положительный элемент.
b=[1,0,1,0,1,1]
4
Построим префиксные суммы индикаторов.
q=[0,1,1,2,2,3,4]
5
Для отрезка от 1 до 4 используем ту же формулу.
\(\displaystyle C(1,4)=q_4-q_0=2-0=2\)

Ответ: сумма на \([2;5]\) равна \(10\), а положительных элементов на \([1;4]\) — \(2\).

Python
1a = [4, -2, 7, 0, 5, 3]
2n = len(a)
3p = [0] * (n + 1)
4for i in range(1, n + 1):
5    p[i] = p[i - 1] + a[i - 1]
6
7l, r = 2, 5
8segment_sum = p[r] - p[l - 1]
9
10q = [0] * (n + 1)
11for i in range(1, n + 1):
12    q[i] = q[i - 1] + (1 if a[i - 1] > 0 else 0)
13positive_count = q[4] - q[0]
Микро-проверка

Как вычислить сумму элементов массива на отрезке \([4;9]\) по префиксным суммам?

Среднее, максимум и несколько условий

Среднее арифметическое на отрезке находится через сумму и количество элементов. Для обычного массива количество равно длине отрезка. Если требуется среднее только по элементам, удовлетворяющим условию, отдельно строят префиксную сумму значений и префиксный счётчик подходящих элементов. Подробный приём разобран на странице среднее по условию.

\[\operatorname{avg}(l,r)=\frac{p_r-p_{l-1}}{r-l+1}\]5

Префиксные суммы не подходят напрямую для максимума или минимума: разность двух префиксных максимумов не даёт максимум на отрезке. Для таких запросов используют отдельные структуры и приёмы, например префиксный максимум и префиксный минимум. Если условие зависит от двух концов или нужно искать пару, полезны поиск пары элементов и два указателя.

Как выбрать способ

Сначала определите, что спрашивают: сумму, количество или экстремум. Для суммы заменяйте элементы их значениями, для количества — нулями и единицами, для среднего храните и сумму, и количество. Для поиска пары или тройки не пытайтесь автоматически применять префиксную сумму: проверьте структуру условия.

Реализация и оценка сложности

При нумерации с нуля часто используют массив префиксов длины \(n+1\): \(p[0]=0\), а элемент \(a[i]\) добавляют в \(p[i+1]\). Тогда сумма элементов с индексами \(l\) до \(r\) включительно равна \(p[r+1]-p[l]\). Такая запись уменьшает число особых случаев, особенно для отрезка, начинающегося с первого элемента.

\[P[i+1]=P[i]+a[i],\qquad S(l,r)=P[r+1]-P[l]\]6

Построение одного префиксного массива требует \(O(n)\) времени и \(O(n)\) памяти. После этого каждый запрос суммы или количества занимает \(O(1)\). Если запросов \(m\), общая сложность равна \(O(n+m)\) вместо \(O(nm)\) в худшем случае при полном переборе каждого отрезка.

!
Частые ошибки

1. Вычитать \(p_l\) вместо \(p_{l-1}\) при нумерации с единицы. 2. Забывать, что правый конец отрезка включён. 3. Считать количество элементов как \(r-l\), хотя правильно \(r-l+1\). 4. Использовать целочисленное деление при вычислении среднего. 5. Строить счётчик только для одного условия, хотя запросы могут требовать другого. 6. Переполнять 32-битный тип при больших значениях: для сумм используйте 64-битные целые.

Запомнить

Префикс отвечает за начало массива. Чтобы оставить отрезок \([l;r]\), берём «до правой границы» минус «до элемента перед левой границей»: \(p_r-p_{l-1}\).

Связь с другими задачами

В задачах экзамена запросы могут быть спрятаны в условии: например, нужно обработать много строк, найти пары или тройки элементов, подсчитать символы с нужным свойством или вычислить условную сумму. Для строк тот же принцип работает после замены символа на индикатор: \(b_i=1\), если символ подходит, и \(0\) иначе. Для более сложных условий пригодится обработка массива по условию, а для суммы только подходящих значений — условная сумма.

Q
Быстрый тест по теме

Быстрая проверка

~ 2 мин4 вопроса
Вопрос 1 / 4
Вопрос 1 из 4 · определение
Что хранит \(p_0\) в стандартном префиксном массиве?
Главное за минуту

Главное

  • Префиксная сумма: \(p_0=0\), \(p_i=p_{i-1}+a_i\).
  • Сумма на отрезке \([l;r]\): \(p_r-p_{l-1}\).
  • Количество подходящих элементов получают префиксной суммой индикаторов 0/1.
  • Для среднего нужны сумма и количество; максимум и минимум требуют других методов.
  • Предварительная обработка занимает \(O(n)\), один запрос — \(O(1)\), все \(m\) запросов — \(O(n+m)\).