我正在尝试编写查询以获取特定销售的开始和结束序列
Serial Sale_id
0001 1
0002 1
0003 1
0004 2
0005 2
0006 1
0007 1
0008 1
我正在寻找像
这样的结果Quantity Start End
3 0001 0003
3 0006 0008
有人可以帮我把这个弄好吗
答案 0 :(得分:2)
此查询(改编自本书SQL MVP Deep Dives)应该可以为您提供所需内容:
SELECT
Sale_id, --optional, include is you want the Sale_id
-- if Serial is a (VAR)CHAR type use this field
Quantity = MAX(CAST(Serial AS INT)) - MIN(CAST(Serial AS INT)) + 1,
-- if Serial is INT already use this field instead
--Quantity = MAX(CAST(Serial AS INT)) - MIN(CAST(Serial AS INT)) + 1,
[Start] = MIN(Serial),
[End] = MAX(Serial)
FROM (
SELECT
Sale_id,
Serial,
RowNumber =
Serial - ROW_NUMBER() OVER (PARTITION BY Sale_id ORDER BY Serial)
FROM YourTable
) a
--WHERE Sale_id = 1 -- optional limiting WHERE clause
--WHERE Sale_id IN (1,2) -- optional limiting WHERE clause
GROUP BY Sale_id, RowNumber
ORDER BY Start;
我假设Serial
存储为字符类型并包含对INT的强制转换。如果它已经是数字类型,请更改为没有Quantity
的强制转换的行。
我选择在输出中加入Sale_id
列,如果您不想要它,只需将其注释掉即可。如果您希望将结果限制为一个或多个特定Sale_id
,请包含WHERE
子句中的一个。
示例输出:
Sale_id Quantity Start End
----------- ----------- ---------- ----------
1 3 0001 0003
2 2 0004 0005
1 3 0006 0008
(3 row(s) affected)
答案 1 :(得分:1)
您可以通过在每个销售ID之前计算非类似销售ID的数量来实现此目的。对于销售ID相同的序列,这是常量。然后使用它进行分组:
select count(*), min(serial_no), max(serial_no)
from (select t.*,
(select count(*)
from taple t2
where t2.serial_no <= t.serial_no and
t2.sale_id <> t.sale_id
) as grp
from taple t
) t
group by grp;
如果您只关心sale_id = 1
,那么在中间子查询查询中添加where
子句。
Here是一个SQL小提琴。