Мне нужна помощь в сокращении времени запроса сложного выражения выбора CASE (с подзапросами) - PullRequest
1 голос
/ 18 марта 2019

Я пытаюсь сделать запрос быстрее.Запрос огромен, но я думаю, что основное внимание должно быть сосредоточено на сложной части запроса CASE.

        (CASE 
            WHEN (SELECT
                g2.montant_ht_actualise_echeance 
            FROM
                base_gid g2 
            WHERE
                g.num_contrat = g2.num_contrat 
                AND g.code_nidt = g2.code_nidt 
                AND g.libelle_rubrique_echeance = g2.libelle_rubrique_echeance 
                AND g.nom_tiers = g2.nom_tiers 
                AND (
                    g.year_echeance - g2.year_echeance
                ) = 1 LIMIT 1) IS NULL THEN g.montant_ht_actualise_echeance 
            WHEN g.montant_ht_actualise_echeance > ((SELECT
                g4.montant_ht_actualise_echeance 
            FROM
                base_gid g4 
            WHERE
                g.num_contrat = g4.num_contrat 
                AND g.code_nidt = g4.code_nidt 
                AND g.libelle_rubrique_echeance = g4.libelle_rubrique_echeance 
                AND g.nom_tiers = g4.nom_tiers 
                AND (
                    g.year_echeance - g4.year_echeance
                ) = 1 LIMIT 1) * 1.1) THEN g.montant_ht_actualise_echeance 
            WHEN g.code_indice LIKE 'ICC%' 
            OR g.code_indice = '' THEN CASE 
                WHEN g.periode_courante_indice_echeance IN (SELECT
                    indice_icc.icc_periode 
                FROM
                    indice_icc) THEN ROUND(g.montant_ht_actualise_echeance,
                2) 
                ELSE ROUND((g.montant_ht_actualise_echeance * :filtre_indice_icc),
                2) 
            END 
            ELSE g.montant_ht_actualise_echeance 
        END) montant_ht_actualise_echeance 

Логика оператора case следующая:

Я пытаюсь отредактироватьстолбец 'montant_actualise_echeance'

  • СЛУЧАЙ 1: Нет счета за предыдущий год -> без изменений на 'montant_actualise_echeance'

  • СЛУЧАЙ 2: Предыдущий годbill * 1.1 меньше или равен montant_actualise_echeance -> без изменений в 'montant_actualise_echeance'

  • Случай 3: если столбец icc подобен ICC ... или пуст:

    • Если в таблице icc есть метка времени текущей строки -> без изменений 'montant_actualise_echeance'

    • Остальное -> montant_ht_actualise_echeance * icc (ввод пользователя)

  • ELSE -> без изменений в 'montant_actualise_echeance'

Вот результат EXPLAIN: EXPLAIN query result

Я использую MariaDB 10.1

1 Ответ

0 голосов
/ 18 марта 2019

Я бы начал с того, что ваш подзапрос может использовать «конверсионный индекс».Индекс, который я уверен, существует, должен быть примерно таким:

create index ix1 on base_gid (
  num_contrat, code_nidt, libelle_rubrique_echeance,
  nom_tiers, year_echeance, montant_ht_actualise_echeance
);

Другой полезный индекс (если у вас его еще нет):

create index ix2 on indice_icc (icc_periode);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...