У меня есть таблица с обменными курсами, которые обновляются только тогда, когда приходит новый обменный курс, то есть фиксируется только дата ввода нового курса. однако у системы есть логика, чтобы сказать, если какая-либо дата попадает в определенную дату, она выбирает соответствующий обменный курс.
я хотел бы иметь запрос, который выбирает требуемый обменный курс с учетом любой предоставленной даты, т. е. выбирает курс из периода.
WITH ListDates(AllDates) AS
( SELECT cast('2015-11-01' as date) AS DATE
UNION ALL
SELECT DATEADD(DAY,1,AllDates)
FROM ListDates
WHERE AllDates < getdate())
SELECT ld.AllDates,cr.effective_from,cr.rate_against_base
FROM ListDates ld
left join CurrencyRatetable cr on cr.effective_from between cr.effective_from and ld.alldates
option (maxrecursion 0)
Добро пожаловать! Не могли бы вы прочитать о проблемах с изображениями изображений текста , а затем отредактировать , чтобы преобразовать ваши изображения таблиц в таблицы разметки? См. /editing-help#tables , чтобы узнать, как это сделать. Вам может пригодиться tablegenerator.com.
Используйте BETWEEN x and y
и убедитесь, что дата x лишена всех данных о времени, а дата y не имеет времени ни на секунду за пределами диапазона, потому что значения здесь являются инклюзивными.
Я думаю, вы можете захотеть добиться требуемого результата, используя оконную функцию LEAD
. Следуя примеру:
DECLARE @t TABLE(effective_from date, rate_against_base decimal(19,4))
INSERT INTO @t VALUES
('2000-01-01', 1.6)
,('2016-10-26', 1)
,('2020-07-13', 65.8765);
DECLARE @searchDate DATE = '2023-01-17';
WITH cte AS(
SELECT effective_from
,ISNULL(LEAD(effective_from) OVER (ORDER BY effective_from), CAST('2049-12-31' AS DATE)) AS effective_to
,rate_against_base
FROM @t
)
SELECT rate_against_base
FROM cte
WHERE @searchDate >= effective_from
AND @searchDate < effective_to
Вы можете использовать CROSS APPLY
или OUTER APPLY
вместе с подзапросом TOP 1
.
Что-то вроде:
WITH ListDates(AllDates) AS (
SELECT cast('2015-11-01' as date) AS DATE
UNION ALL
SELECT DATEADD(DAY,1,AllDates)
FROM ListDates
WHERE AllDates < getdate()
)
SELECT ld.AllDates, cr.effective_from, cr.rate_against_base
FROM ListDates ld
OUTER APPLY (
SELECT TOP 1 *
FROM CurrencyRatetable cr
WHERE cr.effective_from <= ld.alldates
ORDER BY cr.effective_from DESC
) cr
ORDER BY ld.AllDates
option (maxrecursion 0)
И CROSS APPLY
, и OUTER APPLY
похожи на соединение с подзапросом. Разница в том, что CROSS APPLY
похоже на внутреннее соединение, а OUTER APPLY
— на левое соединение.
Убедитесь, что у CurrencyRatetable есть индекс Effective_from для эффективного доступа.
Смотрите эту скрипку db<>.
Предоставление данных вместо их изображений помогает гораздо быстрее получать рекомендации от сообщества. Это одна из причин, по которой вы получаете отрицательный голос.