sql 获取分组第一行数据
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了sql 获取分组第一行数据相关的知识,希望对你有一定的参考价值。
依据namec,medicinemodel,outlookc,memo2分组,按照BidPrice排序,需获取每个分组的第一行,sql语句要怎么写?
是oracle数据库是这样写:select namec,medicinemodel,outlookc,memo2 from (select namec,medicinemodel,outlookc,memo2 from 表名 group by namec,medicinemodel,outlookc,memo2 order by BidPrice) where rownum = 1;
这样就查出第一行的数据 参考技术A DB2/ORACLE/ SQL SERVER 2005以上
select *
from (SELECT namec, medicinemodel,outlookc,memo2, row_number() over(partition by namec,medicinemodel,outlookc,memo2 order by BidPrice) rk from tab) t
where rk = 1追问
表data_center里面有字段:namec(通用名),medicinemodel(剂型),outlookc(规格),memo2(转换系数),jkycj(生产企业) ,BidPrice(中标价),projectnamee(项目名称);要输出的结果是:namec(通用名),medicinemodel(剂型),outlookc(规格),memo2(转换系数),maxjkycj(最高价生产企业) ,maxBidPrice(最高中标价),maxprojectnamee(最高价项目名称),minjkycj(最低价生产企业) ,minBidPrice(最低中标价),minprojectnamee(最低价项目名称)。
追答上面是思路,你要分组的就放到
partition by namec,medicinemodel,outlookc,memo2 后面,排序的放到orer by后面就可以了,自己搞下拉。
SQL Server 获取构成聚合的第一行和最后一行
【中文标题】SQL Server 获取构成聚合的第一行和最后一行【英文标题】:SQL Server Getting First & Last Row that makes up aggregation 【发布时间】:2011-11-22 02:39:20 【问题描述】:我有一个存储一分钟内价格变动数据的表格。每条记录包含最后一分钟的开盘价、最高价、最低价、收盘价和成交量
CREATE TABLE TimeBar (
Instrument varchar(20),
BarTimeStamp datetimeoffset(7),
Open decimal(18, 5),
High decimal(18, 5),
Low decimal(18, 5),
Close decimal(18, 5),
Volume int
)
我要做的是创建一个查询,我可以在其中将数据聚合到更高的时间范围内,例如,我希望能够显示每个小时的开盘价、最高价、最低价和收盘价。
以下是我目前的查询,我已经设法获得了最高价和最低价,但是您如何获得开盘价和收盘价?
SELECT MIN(BarTimeStamp) AS TimeStamp,
MAX(High) AS High,
MIN(Low) AS Low,
SUM(Volume) AS Volume
FROM TimeBar
WHERE Instrument = 'XYZ'
GROUP BY DATEPART(YEAR, BarTimeStamp), DATEPART(MONTH, BarTimeStamp), DATEPART(DAY, BarTimeStamp), DATEPART(HOUR, BarTimeStamp)
【问题讨论】:
【参考方案1】:将主查询用作子查询,为每条记录获取最小时间戳和最大时间戳,因此为它们获取各自的开盘价和收盘价。
SELECT x.*, TI.Open, TE.Close
FROM
(
SELECT Instrument,
MIN(BarTimeStamp) AS TimeStampIni,
MAX(BarTimeStamp) AS TimeStampEnd,
MAX(High) AS High,
MIN(Low) AS Low,
SUM(Volume) AS Volume
FROM TimeBar
GROUP BY Instrument, DATEPART(YEAR, BarTimeStamp), DATEPART(MONTH, BarTimeStamp), DATEPART(DAY, BarTimeStamp), DATEPART(HOUR, BarTimeStamp)
) x
inner join TimeBar TI on ti.Instrument = x.Instrument AND TI.BarTimeStamp = x.TimeStampIni
inner join TimeBar Te on te.Instrument = x.Instrument AND Te.BarTimeStamp = x.TimeStampEnd
【讨论】:
谢谢,正是我想要的。【参考方案2】:首先要做的是按时间范围分组:
SELECT MIN(BarTimeStamp) AS StartTimeStamp,
MAX(BarTimeStamp) AS EndTimeStamp
FROM #TimeBar
WHERE Instrument = 'TEST'
GROUP BY DATEPART(YEAR, BarTimeStamp), DATEPART(MONTH, BarTimeStamp), DATEPART(DAY, BarTimeStamp), DATEPART(HOUR, BarTimeStamp)
之后,问题是:
进行连接以获取范围, 进行连接以开始 进行连接以获得最小值 按原始范围分组以选择所有内容我喜欢使用公用表表达式来简化:
;WITH times as (
SELECT MIN(BarTimeStamp) AS StartTimeStamp,
MAX(BarTimeStamp) AS EndTimeStamp
FROM #TimeBar
WHERE Instrument = 'TEST'
GROUP BY DATEPART(YEAR, BarTimeStamp), DATEPART(MONTH, BarTimeStamp), DATEPART(DAY, BarTimeStamp), DATEPART(HOUR, BarTimeStamp)
)
SELECT
StartTimeStamp as TimeStamp
,MIN([first].[Open]) as [Open]
,MAX(ranged.High) as High
,MAX(ranged.Low) as Low
,MIN([last].[Close]) as [Close]
,SUM(ranged.Volume) as Volume
FROM times
INNER JOIN #TimeBar ranged ON times.StartTimeStamp <= ranged.BarTimeStamp AND times.EndTimeStamp >= ranged.BarTimeStamp
INNER JOIN #TimeBar [first] ON times.StartTimeStamp = [first].BarTimeStamp
INNER JOIN #TimeBar [last] ON times.EndTimeStamp = [last].BarTimeStamp
GROUP BY [times].StartTimeStamp
这是我的测试数据:
CREATE TABLE #TimeBar (
Instrument varchar(20),
BarTimeStamp datetimeoffset(7),
[Open] decimal(18, 5),
High decimal(18, 5),
Low decimal(18, 5),
[Close] decimal(18, 5),
Volume int
)
insert into #TimeBar values ('TEST', '2011-11-21 1:00', 5, 6, 4, 8, 100)
insert into #TimeBar values ('TEST', '2011-11-21 1:10', 1, 7, 3, 4, 100)
insert into #TimeBar values ('TEST', '2011-11-21 2:10', 15, 16, 17, 18, 100)
insert into #TimeBar values ('TEST', '2011-11-21 2:30', 12, 16, 17, 19, 100)
insert into #TimeBar values ('TEST', '2011-11-21 2:50', 13, 14, 15, 20, 100)
结果是:
TimeStamp Open High Low Close Volume
---------------------------------- --------------------------------------- --------------------------------------- --------------------------------------- --------------------------------------- -----------
2011-11-21 01:00:00.0000000 +00:00 5.00000 7.00000 4.00000 4.00000 200
2011-11-21 02:10:00.0000000 +00:00 15.00000 16.00000 17.00000 20.00000 300
注意,我为此使用了一个临时表,只需将 #TimeBar 更改为 TimeBar 即可为您的真实表更改它。
除此之外,我不喜欢将Instrurment varchar
视为字段定义。您应该为此使用surrogate key。
【讨论】:
以上是关于sql 获取分组第一行数据的主要内容,如果未能解决你的问题,请参考以下文章
按一个变量排序,按另一个分组,然后在 R 中的 SQL Query 中选择第一行