Оптимизировать запрос выбора SQL в цикле - PullRequest
0 голосов
/ 10 декабря 2018

Я хочу оптимизировать запрос на выборку в цикле процедуры SQL.Цикл повторяется около 10000 раз, а запрос выбора занимает ок.30 мс для каждой итерации, что увеличивает общее время выполнения процедуры

SELECT *
FROM BANKACCOUNTS B,
     MAPPING M,
     UPL_DTR_UPLOAD UP,
     (SELECT * FROM MAPPING WHERE SOURCE = 'KARVY_BANK_CODE') M1
 WHERE B.SCHEME_CODE = M.INTERNALCODE
   AND M1.INTERNALCODE = B.BANK_CODE
   AND M.SOURCE        = 'R0'
   AND B.AC_TYPE       = 'FUNDING'
   AND M.EXTERNALCODE IS NOT NULL
   AND UPPER(TRIM(M.EXTERNALCODE || M1.EXTERNALCODE || B.AC_NO)) =
           Upper(UP.Scheme || UP.Fundingbnk || UP.fundingacc);

Ответы [ 2 ]

0 голосов
/ 10 декабря 2018

Как упоминает @LoztInSpace, вы почти наверняка можете заменить свой цикл PL / SQL на итерацию «около 10 000 раз», чтобы стать движущим запросом.IE: если вам нужно что-то сделать с результатами из каждой строки, возвращенной в вашем запросе, который вы разместили, для каждой строки в «сделать что-то около 10 000 раз», которая подразумевает, что внешний цикл - это другой запрос, то вложите свой запрос (ну, Кедарверсия запроса) внутри вашего внешнего цикла.

При каждом выполнении цикла PL / SQL должен вызываться механизм SQL, что вызывает переключение контекста;это, вероятно, 10 мс из ваших 30 мс, если не больше.Поиск https://asktom.oracle.com с ключевыми словами PL/SQL "nested loop" для примеров.

Вы также можете посмотреть PL / SQL операторы массовой обработки FORALL и BULK COLLECT для возможных улучшений.

0 голосов
/ 10 декабря 2018

Существует множество решений

  1. Но сначала используйте современные явные объединения.

  2. Ваш запрос для столбца m1 содержит *,используйте только обязательные столбцы

  3. Проверьте план объяснения и используйте индекс

Код:

SELECT * 
FROM bankaccounts B 
JOIN mapping M ON B.scheme_code = M.internalcode 
JOIN 
    (SELECT internalcode, externalcode
     FROM mapping 
     WHERE source = 'KARVY_BANK_CODE') M1 ON M1.internalcode = B.bank_code 
JOIN upl_dtr_upload UP ON UPPER(TRIM(M.externalcode || M1.externalcode || B.ac_no)) = UPPER(UP.scheme || UP.fundingbnk || UP.fundingacc) 
WHERE  
    M.source = 'R0' 
    AND B.ac_type = 'FUNDING' 
    AND M.externalcode IS NOT NULL; 
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...