如何比较SQL Server中的前两行
我有以下表格作为示例: MTRL表如何比较SQL Server中的前两行,sql,sql-server,sql-server-2008,Sql,Sql Server,Sql Server 2008,我有以下表格作为示例: MTRL表 |MTRL| CODE | --------------- | 1 | 080109 | | 2 | 085145 | | 3 | 084141 | MTRLINES表 |MTRL| PRICE | FINDOC | ------------------------- | 1 | 4.95 | 12345 | | 1 | 4.50 | 23421 | | 1 | 3.90 | 23499 | |MTRL| P
|MTRL| CODE |
---------------
| 1 | 080109 |
| 2 | 085145 |
| 3 | 084141 |
MTRLINES表
|MTRL| PRICE | FINDOC |
-------------------------
| 1 | 4.95 | 12345 |
| 1 | 4.50 | 23421 |
| 1 | 3.90 | 23499 |
|MTRL| PRICE | FINDOC |
-------------------------
| 2 | 2.95 | 45345 |
我目前正在使用这两个查询,然后将输出存储到一个变量中。我正在和编程做比较但与其运行两个查询,不如运行一个查询,然后获取输出。
所以我想比较一下最后两个价格。如果上一个价格发生了重大变化,或者只有一个价格如mtrl2,则输出价格为1
SELECT
, SUB.PRICE
FROM (
SELECT
, ML.PRICE
, rn = row_number() over (PARTITION BY M.CODE ORDER BY FINDOC DESC)
FROM MTRLINES ML
INNER JOIN MTRL M
ON M.MTRL = ML.MTRL AND FINDOC IN (SELECT FINDOC FROM FINDOC WHERE SOSOURCE=1251 AND FPRMS IN (1,2))
WHERE M.SODTYPE=51 AND M.COMPANY=1 AND M.CODE=:kod_an
) sub
WHERE rn IN (1)
这存储在变量price1
SELECT
, SUB.PRICE
FROM (
SELECT
, ML.PRICE
, rn = row_number() over (PARTITION BY M.CODE ORDER BY FINDOC DESC)
FROM MTRLINES ML
INNER JOIN MTRL M
ON M.MTRL = ML.MTRL AND FINDOC IN (SELECT FINDOC FROM FINDOC WHERE SOSOURCE=1251 AND FPRMS IN (1,2))
WHERE M.SODTYPE=51 AND M.COMPANY=1 AND M.CODE=:kod_an
) sub
WHERE rn IN (2)
这存储在变量price2
我正在做一些编程(这是vbscript):
仅使用SQL如何实现这一点?试试这样的方法。没有在缺少样本数据的情况下测试它,但是想法是首先在CTE中获得两行(rn=1和rn=2)。然后使用
case
语句查找abs
值,并为rn=
返回0
或PRICE
另外,我假设您的其余查询是正确的
;with t as (
SELECT
SUB.PRICE
FROM (
SELECT
ML.PRICE
, rn = row_number() over (PARTITION BY M.CODE ORDER BY FINDOC DESC)
FROM MTRLINES ML
INNER JOIN MTRL M
ON M.MTRL = ML.MTRL AND FINDOC IN (SELECT FINDOC FROM FINDOC WHERE SOSOURCE=1251 AND FPRMS IN (1,2))
WHERE M.SODTYPE=51 AND M.COMPANY=1 AND M.CODE=:kod_an
) sub
WHERE rn IN (1,2)
)
select case
when abs(sum(case when rn=1
then price
else (price * -1 )
end)
)
> 0.02
then (select price1 from t where rn=1)
else 0 end
as result
from t
;
试试这样的。没有在缺少样本数据的情况下测试它,但是想法是首先在CTE中获得两行(rn=1和rn=2)。然后使用
case
语句查找abs
值,并为rn=
返回0
或PRICE
另外,我假设您的其余查询是正确的
;with t as (
SELECT
SUB.PRICE
FROM (
SELECT
ML.PRICE
, rn = row_number() over (PARTITION BY M.CODE ORDER BY FINDOC DESC)
FROM MTRLINES ML
INNER JOIN MTRL M
ON M.MTRL = ML.MTRL AND FINDOC IN (SELECT FINDOC FROM FINDOC WHERE SOSOURCE=1251 AND FPRMS IN (1,2))
WHERE M.SODTYPE=51 AND M.COMPANY=1 AND M.CODE=:kod_an
) sub
WHERE rn IN (1,2)
)
select case
when abs(sum(case when rn=1
then price
else (price * -1 )
end)
)
> 0.02
then (select price1 from t where rn=1)
else 0 end
as result
from t
;
我可以建议:
with prices as (
select code,
max(case when seqnum = 1 then price end) as price_last,
max(case when seqnum = 2 then price end) as price_second,
count(*) as num_prices
from (select ml.price, m.code,
row_number() over (partition by M.CODE order by FINDOC desc) as seqnum
from MTRLINES ML inner join
MTRL M
ON M.MTRL = ML.MTRL and
FINDOC in (select FINDOC from FINDOC where SOSOURCE = 1251 and FPRMS in (1, 2)
)
where M.SODTYPE = 51 and M.COMPANY = 1 and
M.CODE = :kod_an
) m
where seqnum in (1, 2)
group by code
)
select (case when num_prices = 1 then price_last
when abs(price_last - price_second) > 0.02 then price_last
else 0
end)
from prices;
请注意,您的代码一次只执行一个代码。您可以删除M.code=:kod\u an
并在多个代码上运行代码。我建议:
with prices as (
select code,
max(case when seqnum = 1 then price end) as price_last,
max(case when seqnum = 2 then price end) as price_second,
count(*) as num_prices
from (select ml.price, m.code,
row_number() over (partition by M.CODE order by FINDOC desc) as seqnum
from MTRLINES ML inner join
MTRL M
ON M.MTRL = ML.MTRL and
FINDOC in (select FINDOC from FINDOC where SOSOURCE = 1251 and FPRMS in (1, 2)
)
where M.SODTYPE = 51 and M.COMPANY = 1 and
M.CODE = :kod_an
) m
where seqnum in (1, 2)
group by code
)
select (case when num_prices = 1 then price_last
when abs(price_last - price_second) > 0.02 then price_last
else 0
end)
from prices;
请注意,您的代码一次只执行一个代码。您可以删除
M.code=:kod_an
并在多个代码上运行代码。Hi,它表示无效列名rn
Hi,它表示无效列名rn
很好!只需用-
更正
,谢谢!当mtrlines表有一行时,例如,一个价格返回0。它应该返回Price1。请调查一下。当有两行或更多行时,它会工作。。@F.Mysir。有一种方法计算价格,并在逻辑中明确包含价格。那么我们如何添加if语句,使if mtrlines有一行返回价格1呢?在vbscript中,若第二个查询中并没有第二行,则返回0。所以我对Price1-Price2进行了分解,例如3.45-0>0.02,这是真的,输出为3.45。通过这个查询,我得到了0,在这种情况下,mtrlines有一行,这很好!只需用-
更正
,谢谢!当mtrlines表有一行时,例如,一个价格返回0。它应该返回Price1。请调查一下。当有两行或更多行时,它会工作。。@F.Mysir。有一种方法计算价格,并在逻辑中明确包含价格。那么我们如何添加if语句,使if mtrlines有一行返回价格1呢?在vbscript中,若第二个查询中并没有第二行,则返回0。所以我对Price1-Price2进行了分解,例如3.45-0>0.02,这是真的,输出为3.45。通过这个查询,如果mtrlines有一行,我得到0