Добавить в корзинуПозвонить
Найти в Дзене
Postgres DBA

Методика оптимизации механизма забывания для редких инцидентов

Материал подготовлен нейросетью DeepSeek.
Свойство адаптивности цепи Маркова
Текущие настройки забывания
Механизм адаптивного забывания
Оглавление

Материал подготовлен нейросетью DeepSeek.

Введение

Свойство адаптивности цепи Маркова

Текущие настройки забывания

Механизм адаптивного забывания

Проблема

При текущих настройках:

  • alpha = 0.1, interval_minute = 30 → каждые полчаса все частоты умножаются на (1 - 0.1) = 0.9.
  • Через 1 неделю (336 половинок = 168 циклов забывания) вес одного наблюдения уменьшается в 0.9^168 ≈ 2.5·10⁻⁸ раз — практически обнуляется.
  • Редкий инцидент (1 раз в 1–2 недели) не успевает «закрепиться» в матрице вероятностей.

Цель

Сохранить статистическую значимость редких переходов в аварийные состояния, не нарушая адаптивности модели к текущим условиям.

-2

☑️1. Адаптивное изменение alpha в зависимости от времени, прошедшего с последнего инцидента

Идея

Динамически уменьшать alpha (скорость забывания), когда инциденты редки, и возвращать к базовому значению, когда они становятся чаще.

Реализация (модификация markov_config и apply_forgetting)

Добавить в markov_config новые параметры:

ALTER TABLE markov_config ADD COLUMN base_alpha REAL DEFAULT 0.1;

ALTER TABLE markov_config ADD COLUMN min_alpha REAL DEFAULT 0.01;

ALTER TABLE markov_config ADD COLUMN incident_half_life_days REAL DEFAULT 7.0; -- дни, за которые вес инцидента падает вдвое

ALTER TABLE markov_config ADD COLUMN last_incident_time TIMESTAMPTZ;

Создать функцию, обновляющую last_incident_time при каждом переходе в аварийное состояние.

Модифицировать apply_forgetting, чтобы она вычисляла эффективный alpha по формуле:

alpha_effective = base_alpha * (1 - decay_factor)

где decay_factor = exp(- (now() - last_incident_time) / (half_life / ln(2)) ) — но проще использовать готовую эвристику.

Упрощённый вариант:

Если с момента последнего инцидента прошло более N дней, использовать min_alpha, иначе base_alpha.

Пример кода в apply_forgetting:

DECLARE

cfg RECORD;

days_since_incident REAL;

effective_alpha REAL;

BEGIN

SELECT base_alpha, min_alpha, incident_half_life_days, last_incident_time INTO cfg

FROM markov_config LIMIT 1;

IF cfg.last_incident_time IS NULL THEN

effective_alpha := cfg.min_alpha; -- никогда не было инцидента — не забываем

ELSE

days_since_incident := EXTRACT(EPOCH FROM (now() - cfg.last_incident_time)) / 86400.0;

-- alpha уменьшается экспоненциально с периодом полураспада incident_half_life_days

effective_alpha := cfg.base_alpha * exp(-days_since_incident / cfg.incident_half_life_days);

effective_alpha := GREATEST(effective_alpha, cfg.min_alpha);

END IF;

-- Применяем забывание с effective_alpha вместо фиксированного alpha

UPDATE markov_frequencies SET frequency = frequency * (1.0 - effective_alpha);

...

END;

Результат:

Если инцидент был вчера → alpha ≈ base_alpha (быстрое забывание).

Если инцидента не было 2 недели → alpha ≈ min_alpha (почти не забываем, редкие события сохраняются).

-3

❓2. Разделение частот на «фоновые» и «кратковременные»

Идея

Хранить две матрицы частот:

  • markov_frequencies_long — с очень медленным забыванием (alpha = 0.001, период полураспада ~700 циклов или несколько месяцев).
  • markov_frequencies_short — с быстрым забыванием (alpha = 0.1) для улавливания текущего тренда.

При прогнозе комбинировать вероятности, например, с весами 0.3 (долгая) + 0.7 (короткая). Редкие инциденты попадают в долгую память и не теряются.

Реализация

  • Создать таблицу markov_frequencies_long (структура как у markov_frequencies).
  • В log_transition_and_update обновлять обе таблицы.
  • apply_forgetting применяет alpha_short к короткой, и alpha_long (маленькое) к длинной.
  • При вычислении markov_probabilities использовать взвешенную сумму частот:
  • frequency_combined = w * freq_long + (1-w) * freq_short, затем нормализовать.

Преимущество: редкие инциденты живут в долгой памяти месяцами, но текущие изменения учитываются быстро.

-4

📋3. Использование «бустера» важности для редких переходов

Идея

Каждый переход в аварийное состояние получает искусственный «весовой множитель» > 1 при добавлении в markov_frequencies.

В функции update_markov_frequency добавить параметр importance_multiplier, который по умолчанию = 1, а для аварийных переходов = boost_factor (например, 10 или 20).

-- модификация вызова в log_transition_and_update для аварийного to_state

IF (SELECT correlation < 0 AND os_trend = -1 FROM state_descriptions WHERE state_id = to_id) THEN

multiplier := (SELECT incident_boost FROM markov_config); -- например, 10

ELSE

multiplier := 1;

END IF;

INSERT INTO markov_frequencies ... ON CONFLICT DO UPDATE

SET frequency = markov_frequencies.frequency + multiplier;

Важно: при забывании умножение на (1-alpha) применяется ко всем частотам одинаково, но начальный вес аварийного перехода выше, поэтому он исчезнет медленнее.

Недостаток: может исказить реальные вероятности, если бустер слишком велик. Рекомендуется boost_factor = 2..5.

-5

4. Отключение забывания для состояний с очень низкой частотой

Идея

Если для пары (from_state, to_state) частота перехода меньше порога (например, 0.1), не применять к ней забывание — считать такие переходы «памятными» исключениями.

Реализация в apply_forgetting:

UPDATE markov_frequencies

SET frequency = frequency * (1.0 - alpha)

WHERE frequency >= 0.1 OR (to_state IN (SELECT state_id FROM state_descriptions WHERE correlation < 0 AND os_trend = -1));

-- для аварийных переходов забывание применяется всегда, но для очень редких неаварийных — не трогаем

Более чистый вариант: добавить колонку protected BOOLEAN DEFAULT false и в момент добавления аварийного перехода устанавливать protected = true. При забывании обновлять только строки с protected = false.

-6

5. Рекомендуемые параметры для сценария «1 инцидент в 1–2 недели»

Базовый механизм (текущий):

  • alpha = 0,1
  • interval_minute = 30 минут

Адаптивный alpha (пункт 1 методики):

  • min_alpha = 0,005 – 0,01
  • incident_half_life_days = 14 дней
  • (чтобы инцидент терял половину веса за 2 недели)

Бустер важности (пункт 3 методики):

  • incident_boost = 3 – 5
  • (в зависимости от желаемой инерции)

Долгая память (пункт 2 методики):

  • alpha_long = 0,001 – 0,002
  • (период полураспада ~70 дней)
  • вес долгой памяти в прогнозе = 0,2 – 0,3
-7

6. Мониторинг эффективности

После внедрения оптимизации отслеживать:

  • Вес (frequency) аварийных переходов в markov_frequencies через 1, 2, 4 недели после инцидента.
  • Brier Score модели в периоды без инцидентов (не должно резко ухудшаться).
  • Количество срабатываний check_and_forget — не должно вырасти более чем в 2 раза из-за замедленного забывания.
-8

📋Рекомендуется сначала внедрить адаптивный alpha (пункт 1) как наименее инвазивный и наиболее управляемый.

Если проблема сохранится, добавить бустер важности (пункт 3) или долгую память (пункт 2).