docs: документация переведена на канон av-dev-pm
- беклог и план переехали в docs/tasks (38 задач, 11 целей), слаги переименованы с транслита на английские, 85 ссылок поправлены - conventions.md разобран в docs/conventions/, local-research.md — в docs/research/, review-journal.md — в docs/review.md с разделом настройки конвейера; заведены security.md, adr/ и .pm.json - шаг docs.py check добавлен в task gate; поведение в architecture.md помечено девятью маркерами долга, database.md получил настройки с числовым значением
This commit is contained in:
@@ -0,0 +1,91 @@
|
||||
# Тай-брейк при равной полноте точек
|
||||
|
||||
**Секция:** ядро · **Хук:** Решено: брать бо́льшее значение. Порядок канонических форм берёт меньшее в 96% случаев — для накопительных это систематический недосчёт · **Теги:** goal:merge-robustness, question
|
||||
|
||||
**Решение принято владельцем 2026-08-02: вариант (б) — брать бо́льшее значение
|
||||
точки.** Ниже — исходная постановка блокера, она же ТЗ; рекомендация в конце
|
||||
файла и есть выбранный вариант.
|
||||
|
||||
Что важно не потерять при реализации: правило обязано остаться **тотальным** —
|
||||
числа у точки нет, значит откат на порядок канонических форм, — и обязано
|
||||
остаться полурешёткой: `max` коммутативен, ассоциативен и идемпотентен, поэтому
|
||||
воспроизводимость свёртки не страдает. Род агрегации в правило **не входит**:
|
||||
род есть функция витрины, и правило слияния, читающее собственную выдачу,
|
||||
повторяет дефект наследования слоя «из будущего» (`docs/review.md`,
|
||||
2026-08-01).
|
||||
|
||||
Приёмка та, что названа ниже: на прогоне живого архива отпечаток витрины обязан
|
||||
**измениться** (иначе правило не сработало), а число столкновений с равной
|
||||
полнотой — остаться прежним.
|
||||
|
||||
## Вопросы
|
||||
Какое правило выбирает победителя, когда по одним координатам приехали две точки
|
||||
с **равными** наборами содержательных полей и разными значениями. Структурная
|
||||
часть правила слияния закрыта (`pravilo-sliyaniya-tochek`); открыт только этот
|
||||
разряд.
|
||||
|
||||
Сегодня это порядок канонических форм, и он измеримо смещён: из 1912 случаев, где
|
||||
сравнение чисел определено, лексикографический порядок берёт **меньшее** значение
|
||||
в 1847 — 96% (находка 49). Столкновений с равной полнотой 1916 из 444 256
|
||||
координат, то есть 0.43% координат.
|
||||
|
||||
## Что стало известно
|
||||
|
||||
Задача «Измеренный род агрегации и каталог разрезов» закрыла посылку, ради
|
||||
которой тай-брейк откладывали: род метрик теперь **измерен**, а не угадан
|
||||
(находка 53). Четыре из шести метрик, где тай-брейк системно берёт меньшее
|
||||
(`step_count`, `walking_running_distance`, `active_energy`,
|
||||
`basal_energy_burned`), измерены как **накопительные** — там «меньшее» это
|
||||
систематический недосчёт порядка 0.4% координат, ровно тот, что HAE досчитывает
|
||||
задним числом (находка 10). Самая крупная группа, `heart_rate`, измерена как
|
||||
**мгновенная**, и там выбор безразличен: это пересэмплирование, а не досчёт.
|
||||
|
||||
И тем же измерением закрылся напрашивавшийся ответ: **сделать тай-брейк
|
||||
зависящим от измеренного рода нельзя**. Род есть функция витрины, витрина —
|
||||
результат слияния, и правило слияния, читающее собственную выдачу, повторяет
|
||||
ровно тот дефект, на котором свёртка уже переставала быть функцией префикса
|
||||
журнала (`docs/review.md`, 2026-08-01, наследование слоя «из будущего»).
|
||||
|
||||
## Варианты и цена
|
||||
|
||||
**а. Оставить порядок канонических форм.** Цена: систематический недосчёт 0.4%
|
||||
координат у накопительных метрик, невидимый до сверки с родным экспортом Apple,
|
||||
то есть месяцами. Плюс: ноль работы, правило остаётся структурным и не знает
|
||||
ничего о значениях.
|
||||
|
||||
**б. Брать бо́льшее значение точки.** Правильно для накопительных (досчёт растёт,
|
||||
находка 10, и набор полей у версий тренировки ни разу не уменьшался) и безвредно
|
||||
для мгновенных (пересэмплирование). Цена: слияние перестаёт быть структурным —
|
||||
оно начинает знать, какое поле точки несёт число (`hae.PointValue` уже есть).
|
||||
Метрика, у которой «большее» неверно, в потоке не наблюдалась, но и не
|
||||
исключена; правило приходится делать тотальным (нет числа — откат на порядок
|
||||
канонических форм), то есть в нём появляется вторая ветка.
|
||||
|
||||
**в. Провенанс у точки и тай-брейк по позиции в журнале** — как у сущностей.
|
||||
Цена: колонка провенанса на точку (или на объект) и рост объёма нижнего слоя;
|
||||
плюс это не работает для столкновений **внутри одной доставки**, где
|
||||
`received_at` общий, а таких четверть (находка 47: 33 столкновения внутри
|
||||
доставки на эпизодах сна). То есть вариант не самодостаточен и всё равно требует
|
||||
второго разряда.
|
||||
|
||||
## Что заблокировано
|
||||
|
||||
Ничего срочного: сегодняшнее правило детерминировано и воспроизводимо, витрина
|
||||
остаётся свёрткой журнала. Блокирован только сам недосчёт — он копится молча.
|
||||
Сверить его величину можно будет после `healthlog import`: родной экспорт Apple
|
||||
даст независимый эталон по тем же периодам.
|
||||
|
||||
## Рекомендация
|
||||
|
||||
**Вариант б.** Он чинит измеренное смещение там, где оно есть, и не трогает
|
||||
там, где его нет; цена — одна ветка в правиле слияния и признание, что слияние
|
||||
знает про число точки (а оно уже знает — `hae.PointValue` живёт в разборе). От
|
||||
варианта «а» отличается тем, что перестаёт систематически терять данные;
|
||||
от «в» — тем, что не требует ни колонки, ни решения для внутридоставочных
|
||||
столкновений.
|
||||
|
||||
Проверять на прогоне живого архива: отпечаток витрины обязан измениться (иначе
|
||||
правило не сработало), а число столкновений с равной полнотой — остаться прежним.
|
||||
|
||||
Связано: `docs/architecture.md` → «Разрешение столкновений», находки 10, 47, 49,
|
||||
53.
|
||||
Reference in New Issue
Block a user