У меня есть следующая хранимая процедура:
DELIMITER //
CREATE PROCEDURE runAmortization(
IN p_accountNumber varchar(50),
IN p_apr decimal(17,15),
IN p_principalBalanceOfLoan decimal(10,2),
IN p_amountFinancedOfLoan decimal(10,2),
IN p_financeCharge decimal(10,2),
IN p_contractDateOfLoan datetime
)
BEGIN
DECLARE v_bCursorFinished INT DEFAULT 0;
DECLARE v_interestRemaining DECIMAL(8,2) DEFAULT 0;
DECLARE v_effectiveDate datetime;
DECLARE v_previousEffectiveDate datetime;
DECLARE v_principal DECIMAL(18,2) DEFAULT 0;
DECLARE v_type varchar(50);
DECLARE v_principalRemaining DECIMAL(10,2) DEFAULT 0;
DECLARE v_daysBetween int DEFAULT 0;
DECLARE v_varianceAmount DECIMAL(10,2) DEFAULT 0;
DECLARE v_inVariance BIT;
DECLARE transactionsCursor
CURSOR FOR
SELECT
TranEffectiveDate,
Amount,
Upper(Type) as PaymentType
FROM
transactions
WHERE
AccountNumber = p_accountNumber
ORDER BY
TranEffectiveDate ASC;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET v_bCursorFinished = 1;
SET v_principalRemaining = p_amountFinancedOfLoan + COALESCE(p_financeCharge, 0);
SET v_previousEffectiveDate = p_contractDateOfLoan;
DROP TABLE IF EXISTS tblAmortizationResults;
CREATE TEMPORARY TABLE IF NOT EXISTS tblAmortizationResults
(
payment_date DateTime,
payment decimal(10,2),
type varchar(30),
principal_remaining decimal(18,2),
days_between_payment int NULL
);
OPEN transactionsCursor;
FETCH transactionsCursor INTO v_effectiveDate, v_principal, v_type;
INSERT INTO tblAmortizationResults
(payment, payment_date, type, principal_remaining)
VALUES
(0, p_contractDateOfLoan, 'PAYMENT', v_principalRemaining);
runAmort: LOOP
FETCH transactionsCursor INTO v_effectiveDate, v_principal, v_type;
IF v_bCursorFinished = 1 THEN
LEAVE runAmort;
END IF;
SET v_daysBetween = DATEDIFF(v_previousEffectiveDate, v_effectiveDate);
SET v_principalRemaining = v_principalRemaining - v_principal;
INSERT INTO tblAmortizationResults
(payment_date, payment, type, principal_remaining, days_between_payment)
VALUES
(v_effectiveDate, v_principal, v_type, v_principalRemaining, v_daysBetween);
SET v_previousEffectiveDate = v_effectiveDate;
END LOOP runAmort;
CLOSE transactionsCursor;
INSERT INTO amortization
(account_number, payment_date, payment, type, principal_remaining, days_between_payment, created_date)
SELECT
p_accountNumber, payment_date, payment, type, principal_remaining, days_between_payment, CURRENT_TIMESTAMP
FROM tblAmortizationResults;
SET v_varianceAmount = (p_principalBalanceOfLoan - v_principalRemaining);
SET v_inVariance = 0;
IF v_varianceAmount >= -50 AND v_varianceAmount <= 50 THEN
SET v_inVariance = 1;
END IF;
INSERT INTO amortization_variance
(account_number, variance, last_calculated, in_variance)
VALUES
(p_accountNumber, v_varianceAmount, CURRENT_TIMESTAMP, v_inVariance);
END //
DELIMITER ;
Как вы можете видеть, я беру данные из таблицы transactions
, а затем перемещаю курсор по ней, чтобы обработать каждую строку данных. Я использую переменные между каждой итерацией для хранения значений, которые в конечном итоге вставляются в таблицу базы данных.
Я чувствую, что есть способ использовать LEAD()
и LAG()
вместо этого, но не могу понять как ... кто-нибудь может "привести" меня в правильном направлении?
Спасибо за любой вклад