Sql Crystal报表需要按派生日期范围分组
长时间列表,第一次调用。我正在使用Crystal Reports 2010 我有每日交易信息,如果交易量不变,我需要将这些信息组合在一起。下面是数据的样子 交易开始日期结束日期卷 我需要它看起来像这样 交易日期范围卷Sql Crystal报表需要按派生日期范围分组,sql,plsql,group-by,date-range,crystal-reports-2010,Sql,Plsql,Group By,Date Range,Crystal Reports 2010,长时间列表,第一次调用。我正在使用Crystal Reports 2010 我有每日交易信息,如果交易量不变,我需要将这些信息组合在一起。下面是数据的样子 交易开始日期结束日期卷 我需要它看起来像这样 交易日期范围卷 我需要根据导出的日期范围进行分组,但我不确定如何使用Crystal实现这一点。有什么想法吗?我会使用X-2抑制功能来隐藏每一行中除最后一行之外的所有内容,以及上一行和下一行以查找端点 with w as ( select 1 id, to_date('1/1/2012',
我需要根据导出的日期范围进行分组,但我不确定如何使用Crystal实现这一点。有什么想法吗?我会使用X-2抑制功能来隐藏每一行中除最后一行之外的所有内容,以及上一行和下一行以查找端点
with w as (
select 1 id, to_date('1/1/2012', 'mm/dd/yyyy') db, to_date('1/2/2012', 'mm/dd/yyyy') de, 500 s from dual
union all
select 1, to_date('1/2/2012', 'mm/dd/yyyy'), to_date('1/3/2012', 'mm/dd/yyyy'), 500 from dual
union all
select 1, to_date('1/3/2012', 'mm/dd/yyyy'), to_date('1/4/2012', 'mm/dd/yyyy'), 1000 from dual
union all
select 1, to_date('1/4/2012', 'mm/dd/yyyy'), to_date('1/5/2012', 'mm/dd/yyyy'), 750 from dual
union all
select 1, to_date('1/5/2012', 'mm/dd/yyyy'), to_date('1/6/2012', 'mm/dd/yyyy'), 750 from dual
union all
select 1, to_date('1/6/2012', 'mm/dd/yyyy'), to_date('1/7/2012', 'mm/dd/yyyy'), 500 from dual
union all
select 1, to_date('1/7/2012', 'mm/dd/yyyy'), to_date('1/8/2012', 'mm/dd/yyyy'), 500 from dual
union all
select 1, to_date('1/8/2012', 'mm/dd/yyyy'), to_date('1/9/2012', 'mm/dd/yyyy'), 510 from dual
)
select tmin.db, tmax.de, tmin.s
from
(
select
row_number() over (order by db) id,
db,
s
from
(
select
db,
s,
case
when ps is null
then 1
when ps != s
then row_number() over (order by db)
else 0 end num
from (
select
(db)
, (de)
, lag (s,1) over (ORDER BY db) ps
, s
from w
) t
) t1
where num != 0
) tmin,
(select
row_number() over (order by db) id,
de,
s
from
(
select
db,
de,
s,
case
when ps is null
then 1
when ps != s
then row_number() over (order by de desc)
else 0 end num
from (
select
db
,(de)
, lag (s,1) over (ORDER BY de desc) ps
, s
from w
order by db
) t
) t1
where num != 0) tmax
where tmin.id = tmax.id
按起始日期分组;抑制详细信息和组页脚部分
在组头的某个位置创建{@UpdateCurrentBegDate}函数
WhilePrintingRecords;
Global DateVar CurrentBegDate;
If PreviousIsNull({table.Volume}) or Previous({table.Volume}) <> {table.Volume}
Then ( //We found a new range
CurrentBegDate = {table.BegDate};
);
""; //Display nothing on screen
转到节专家,单击组标题节的抑制选项旁边的X-2。这是这里的公式
Not(NextIsNull({table.Volume}) or Next({table.Volume}) <> {table.Volume})
如果需要进行总计或其他计算,可以在{@UpdateCurrentBegDate}函数中进行,并希望将名称更改为{@UpdateCurrentValues}或类似的名称。如果您只想在组更改时更改内容,还可以创建一个新函数来检查下一个信息-使用默认的合计函数将包括隐藏值。这是我能想到的最优雅的解决方案
WITH DirectTrades(tradeid, SourceDate, EndDate, Volume, Row, KillRow, Depth) AS
(
SELECT tradeid
BegDate AS SourceDate,
EndDate,
Volume,
ROW_NUMBER() over (partition by Table# order by BegDate) AS Row,
ROW_NUMBER() over (partition by Table# order by BegDate) AS KillRow,
0 AS Depth
FROM Trade
UNION ALL
SELECT t1.Tradeid
dt.SourceDate,
t1.EndDate,
t1.Volume,
dt.Row,
dt.Row + dt.Depth + 1,
dt.Depth + 1
FROM Trade AS t1
INNER JOIN
DirectTrades AS dt ON
t1.BegDate=dt.EndDate AND
t1.Volume=dt.Volume AND
t1.tradeid=dt.Tradeid
)
SELECT dt1.Tradeid
dt1.SourceDate,
dt1.EndDate,
dt1.Volume
FROM DirectTrades dt1
INNER JOIN
(
SELECT dt2.Row,
MAX(dt2.KillRow) AS KillRow
FROM DirectTrades dt2
WHERE dt2.Row NOT IN
(
SELECT dt3.KillRow
FROM DirectTrades dt3
WHERE dt3.Depth <> 0
)
GROUP BY dt2.Row
) dt4 ON dt1.Row=dt4.Row AND dt1.KillRow=dt4.KillRow
ORDER BY SourceDate
我认为这个问题类似于伟大的,我没有看到我需要一个纯SQL的解决方案,直到张贴这篇文章。不过我不会删除它,它回答了原来的问题。谢谢你的回答。即使我也不会删除它。我身上有一些限制,这就产生了对纯SQL解决方案的需求。我还没有试着测试Stevo的答案。如果有人需要这样的解决方案,我会把你的留在这里+为了你的利益。同时,请确保您得到一个仅基于SQL的解决方案。这将是一个很大的帮助。工作,但不可理解,因此不可复制+1只是为了你的兴趣。工作完美,看起来是完成工作所需的最低代码。仍在寻找更多的解决方案+我得到的最好、最简洁的答案。谢谢+不起作用。我有表名TradeID、BEGDATE、ENDDATE、VOLUME以及问题中描述的数据。请提供符合模式的解决方案,并相应地编辑您的答案。
WhilePrintingRecords;
Global DateVar CurrentBegDate;
If PreviousIsNull({table.Volume}) or Previous({table.Volume}) <> {table.Volume}
Then ( //We found a new range
CurrentBegDate = {table.BegDate};
);
""; //Display nothing on screen
EvaluateAfter({@UpdateCurrentBegDate});
Global DateVar CurrentBegDate;
Not(NextIsNull({table.Volume}) or Next({table.Volume}) <> {table.Volume})
WITH DirectTrades(tradeid, SourceDate, EndDate, Volume, Row, KillRow, Depth) AS
(
SELECT tradeid
BegDate AS SourceDate,
EndDate,
Volume,
ROW_NUMBER() over (partition by Table# order by BegDate) AS Row,
ROW_NUMBER() over (partition by Table# order by BegDate) AS KillRow,
0 AS Depth
FROM Trade
UNION ALL
SELECT t1.Tradeid
dt.SourceDate,
t1.EndDate,
t1.Volume,
dt.Row,
dt.Row + dt.Depth + 1,
dt.Depth + 1
FROM Trade AS t1
INNER JOIN
DirectTrades AS dt ON
t1.BegDate=dt.EndDate AND
t1.Volume=dt.Volume AND
t1.tradeid=dt.Tradeid
)
SELECT dt1.Tradeid
dt1.SourceDate,
dt1.EndDate,
dt1.Volume
FROM DirectTrades dt1
INNER JOIN
(
SELECT dt2.Row,
MAX(dt2.KillRow) AS KillRow
FROM DirectTrades dt2
WHERE dt2.Row NOT IN
(
SELECT dt3.KillRow
FROM DirectTrades dt3
WHERE dt3.Depth <> 0
)
GROUP BY dt2.Row
) dt4 ON dt1.Row=dt4.Row AND dt1.KillRow=dt4.KillRow
ORDER BY SourceDate