В двух выгрузках посчитаны категории A, B и C. Нужно сохранить разность «первое количество минус второе» для каждой категории, включая увеличение и отсутствие изменения. Для такой задачи выражение first - second у Counter может убрать важные строки: в его результате остаются только положительные счётчики.
Категории и количества ниже вымышлены. Перед нами две заранее согласованные сводки одного учебного набора категорий; это не измерение эффекта и не сведения об участниках исследования. В каждой сводке полностью учтены категории A, B и C, неизвестных пропусков здесь нет. Направление разности задано явно: из первого количества вычитается второе.
Три категории с разными знаками разности
| Показатель | Учебный результат |
|---|---|
| A: первое / второе / разность | 3 / 1 / +2 |
| B: первое / второе / разность | 1 / 2 / −1 |
| C: первое / второе / разность | 2 / 2 / 0 |
| Итого: первое / второе / разность | 6 / 5 / +1 |

В категории A первая частота на 2 больше. В B она на 1 меньше, поэтому разность отрицательна. В C количества равны: ноль здесь рассчитанная разность, а не отсутствующее наблюдение. Сумма разностей равна 2 − 1 + 0 = 1, что сходится с 6 − 5 = 1.
В официальной документации Counter различаются арифметическая операция вычитания и метод subtract(). Операция - исключает из результата нулевые и отрицательные счётчики. Метод изменяет сам счётчик и допускает такие результаты. Поэтому для знаковой разности ниже сначала создаётся копия первой сводки.
Полный код и проверяемый вывод
from collections import Counter
first = Counter({"A": 3, "B": 1, "C": 2})
second = Counter({"A": 1, "B": 2, "C": 2})
positive_only = first - second
signed = first.copy()
signed.subtract(second)
print("first", dict(sorted(first.items())))
print("second", dict(sorted(second.items())))
print("minus", dict(sorted(positive_only.items())))
print("subtract", dict(sorted(signed.items())))
print("minus_sum", sum(positive_only.values()))
print("signed_sum", sum(signed.values()))
print("total_difference", sum(first.values()) - sum(second.values()))
Вот результат запуска этого учебного кода:
first {'A': 3, 'B': 1, 'C': 2}
second {'A': 1, 'B': 2, 'C': 2}
minus {'A': 2}
subtract {'A': 2, 'B': -1, 'C': 0}
minus_sum 2
signed_sum 1
total_difference 1
Оператор минуса дал только A со значением 2. Он не сохранил B со значением −1 и C со значением 0. После signed.subtract(second) остались все три результата. Исходный first сохранился благодаря отдельному вызову copy(); сам метод subtract() меняет объект, на котором вызван.
Почему два итога нельзя подменять друг другом
| Показатель | Учебный результат |
|---|---|
| Сумма результата first - second | 2; сумма только положительных разностей |
| Сумма signed после subtract | 1; сумма знаковых разностей всех трёх категорий |
| Разность исходных сумм | 6 − 5 = 1; совпадает со знаковой суммой |
Итог 2 получается не из арифметической ошибки Python, а из другого правила отбора: оставить только положительные значения по каждой категории. Для нашей задачи нужно видеть и отрицательное изменение, и нулевую разность, поэтому выбран второй результат. Смена правила отбора меняет смысл итогового числа.
Знак нельзя толковать без направления сравнения. Здесь −1 у B означает, что в первой сводке на одну единицу меньше, чем во второй. Это не «минус один человек» в исходных данных и не доказательство ошибки наблюдения. Если поменять направление разности, изменится и знак.
Что проверить до сравнения сводок
- Направление нужно согласовать: первая сводка минус вторая или наоборот.
- Убедитесь, что коды категорий в обеих выгрузках означают одно и то же.
- Отделяйте известное нулевое количество от отсутствия сведений о категории.
- Для этой задачи используйте согласованные неотрицательные целые исходные количества.
- Сохраните исходные сводки и отдельно запишите правило, по которому сформирован результат.
При обращении к отсутствующему ключу Counter возвращает нулевой счётчик. Это техническое поведение не доказывает, что в реальной выгрузке категорию проверили и получили нулевую частоту. Если неизвестно, охвачена ли категория, сначала уточните исходную схему, а не подставляйте ноль по умолчанию.
При подготовке таблицы полезно отдельно проверить имена столбцов до DictReader. Там Counter считает повторы заголовков; здесь задача другая — сохранить знаковые разности между двумя уже согласованными сводками. Правило сравнения и выбранный результат запишите в журнале преобразования данных.
Законченный результат упражнения
В итоге для задачи выбрана сводка A: +2, B: −1, C: 0; её сумма равна +1. Вариант, где остался только A: +2, сохранён для сравнения способов, но не выдаётся за полную знаковую разность. Сам по себе ни один из этих учебных результатов не говорит о статистической значимости или о причине различий между реальными группами.
Если следующий этап работы требует анализа собственного исследовательского набора, можно обсудить статистический анализ данных. Передайте исходные сводки и описание категорий, заранее согласовав исследовательский вопрос и объём помощи. Выбор операции над счётчиками не заменяет выбор метода анализа.