Oracle先按周分,当周含两个月份,再按月分,怎么写SQL语句?大神求助!!!

Yvette_QIU 2019-07-09 09:36:00
我现在选择日期条件2019-05-28至2019-06-07(日历:5.27周一,,,6.02周日。6.03周一,,,6.09周日),我想得出的结果是:2019-05-27至2019-05-31、2019-06-01至2019-06-02、2019-06-03至2019-06-09
...全文
3398 50 打赏 收藏 转发到动态 举报
AI 作业
写回复
用AI写文章
50 条回复
切换为时间正序
请发表友善的回复…
发表回复
Yvette_QIU 2019-09-30
  • 打赏
  • 举报
回复
引用 52 楼 nayi_224的回复:
恩。。。怎么看都是1小时sql,2小时上线的东西。多练练吧,一个sql肯定能轻松搞定的。 关键还是你提问的技巧太差了,让人没有下手的欲望。 你应该先自己把问题简化一下,比如只提炼出 用户,“记录数据”的对应时间,并给出只含这些字段的create语句以及足够反应出所有特殊情况的数据的insert语句,再给出结果的示例。这样你应该在7月10号就能交差了,我也能找到饭后娱乐项目。
好吧,受教了
nayi_224 2019-09-30
  • 打赏
  • 举报
回复
恩。。。怎么看都是1小时sql,2小时上线的东西。多练练吧,一个sql肯定能轻松搞定的。 关键还是你提问的技巧太差了,让人没有下手的欲望。 你应该先自己把问题简化一下,比如只提炼出 用户,“记录数据”的对应时间,并给出只含这些字段的create语句以及足够反应出所有特殊情况的数据的insert语句,再给出结果的示例。这样你应该在7月10号就能交差了,我也能找到饭后娱乐项目。
AHUA1001 2019-09-30
  • 打赏
  • 举报
回复
WITH T1 AS (SELECT TO_DATE('2019-01-01','YYYY-MM-DD') D1,TO_DATE('2019-12-31','YYYY-MM-DD') D2 FROM DUAL), T2 AS (SELECT (D1+LEVEL-1) D FROM T1 CONNECT BY LEVEL <= D2-D1 +1), T3 AS (SELECT D, CASE WHEN D = TRUNC(D,'D')+1 THEN 1 WHEN D = TRUNC(D,'MM') THEN 1 ELSE 0 END B, CASE WHEN D = TRUNC(D,'D') THEN 1 WHEN D = LAST_DAY(D) THEN 1 ELSE 0 END E FROM T2 ) , T4 AS (SELECT D ,ROWNUM R FROM (SELECT D FROM T3 WHERE B = 1 )), T5 AS (SELECT D ,ROWNUM R FROM (SELECT D FROM T3 WHERE E = 1 )) SELECT TRUNC(T4.D) D1,TRUNC(T5.D) D2 FROM T4 FULL JOIN T5 ON T5.R = T4.R ORDER BY 1,2 ;
Yvette_QIU 2019-09-29
  • 打赏
  • 举报
回复
在发帖子那周的周末我已解决,当时因为后续有任务,没有及时回复 首先: (我要统计的报表结果,有周期字段、用户字段、总数字段;情况:多个用户在某日的某时有多个记录数据(若统计一天,算一天的数据条数,若统计一周,算七天的数据条数,以此类推,若我的周要分细点,则要实现“2019.7.22至2019.7.28、2019.7.29至2019.07.31、2019.8.1至2019.8.4”,统计周,算对应的‘2019.7.29至2019.07.31’时间范围内的数据条数、算对应的‘2019.8.1至2019.8.4’的数据条数【都是闭区间的--》2019.8.1 00:00:00至2019.8.4 23:59:59】) 然后: 我以为我想要的效果"2019.7.22至2019.7.28、2019.7.29至2019.07.31、2019.8.1至2019.8.4"只能却一定通过SQL语句实现,其实不是的。我可以获取SQL语句得出的结果用Java代码再处理一下,得到图片里“查询结果列表”里的结果!!! 若只考虑:同一用户在同一周的不同日不同时有不同数据,但那一周存在俩个月份(我觉得:先实现这种情况,后面就不难),要实现:统计某用户在一周的记录总数,且周存在俩个月份,要细分) 思路: 若008用户在7.29与7.30的不同时分秒有多个记录操作,00香在8.01的不同时分秒有多个记录操作, 想:7.29-7.31 008 56 8.1-8.04 00香 13【日期 用户 记录总数】 后面改着改着,成这样了: 【注意:第三条与第四条正是简单情况要实现的!!!必须加上to_char(t.sj ,'iw')否则报异常】
select row_number() over(order by to_char(min(t.sj),'YYYY-MM-DD') asc,to_char(max(t.sj),'YYYY-MM-DD') asc,yh.yh asc) xh,
    to_char(min(t.sj),'YYYY-MM-DD') mindt,to_char(max(t.sj),'YYYY-MM-DD') maxdt
     ,TO_CHAR(t.sj, 'iw') zrz--自然周(数字,表示一年的第几周)
       ,yh.yh xm
       ,count(1) zsl,sum(case when t.zt<>0  then 1 else 0 end) as wdq,sum(case when t.zt=0 then 1 else 0 end) as ydq
       from cxx t
       left join YH yh on t.ry=yh.h    
     WHERE  t.sj between to_date('2019-04-25 00:00:00','yyyy-mm-dd hh24:mi:ss') and to_date('2019-09-25 23:59:59','yyyy-mm-dd hh24:mi:ss')      
    group by to_char(t.sj ,'iw'),to_char(t.sj,'mm'),yh.yh; 
第三条的介绍,001用户在自然周zrz=31的mindt至maxdt时间段(闭区间)有数据,总数为56 所以第四条的介绍也是一样的:00香用户在自然周zrz=31的mindt至maxdt时间段(闭区间)有数据,总数为13 mindt至maxdt时间段(闭区间)表示:mindt到maxdt这几天都是有记录数据, mindt与maxdt不一定指的是一周的周一与周日,但一定在该周内, 则用java代码处理一下: 。。。代码蛮多的,反正做判断的思路: mindt大于周的周一,但小于下个月的第一天对应的星期,则mindt值改为周一,maxdt小于周的周日,也小于下个月的第一天对应的星期,则maxdt值改为这个月的最后一天对应的星期, 若mindt大于周一也大于下月第一天对应的星期,maxdt小于周日但大于下月第一天对应的星期,则分别改下月第一天对应的星期、周日 注: 不可能mindt小于下月第一天对应的星期而maxdt大于下月第一天对应的星期, 还要注意若maxdt等于下月第一天对应的星期或周日等等情况。。。。 对,方法很麻烦,但是我真的想不出如何用SQL语句实现,怎么写都会有点问题(不是想要的答案),,,方法很多种就是要花时间研究,但是模块花费时间太长,同事在催进度,我只能这样写
  • 打赏
  • 举报
回复
with data1 as ( select (trunc(sysdate) -level) as days, to_char(sysdate-level,'day') weekday, to_char(sysdate-level+1,'ww') as week, last_day(sysdate-level) as lastday from dual connect by level <=200) select min(days),max(days),week,lastday from data1 group by week,lastday order by week desc
Yvette_QIU 2019-09-25
  • 打赏
  • 举报
回复
引用 40 楼 wildwolv 的回复:
谢谢
Yvette_QIU 2019-09-25
  • 打赏
  • 举报
回复
引用 43 楼 nayi_224 的回复:
[quote=引用 42 楼 ZJHZ_叶 的回复:] [quote=引用 41 楼 nayi_224 的回复:] 这么基础的groupby怎么连model都整出来了
with tab1 as (
select to_date('20190520', 'yyyymmdd') + level dt
  from dual
connect by level <= 20
)
select min(t1.dt),
       max(t1.dt)
  from tab1 t1
 group by to_char(t1.dt, 'mm'), to_char(t1.dt + 1, 'ww')
 order by min(t1.dt)
;
你这个我前面写过了,to_char(,'w')/to_char(,'ww')并不是从周一开始的,而是当月(年)1-7号算一周,然后每7天算一周 [/quote] 那就改成iw呗[/quote]谢谢
Yvette_QIU 2019-09-25
  • 打赏
  • 举报
回复
引用 37 楼 码匀 的回复:
with temp as( select trunc(sysdate)-level createday from dual connect by level<100 ) select substr(listagg (to_char(createday,'yyyy/mm/dd'),'-') WITHIN GROUP (ORDER BY createday),1,10)||'-' ||substr(listagg (to_char(createday,'yyyy/mm/dd'),'-') WITHIN GROUP (ORDER BY createday),-10,10) week ,'' 周一,'' 周二,'' 周三,'' 周四,'' 周五,'' 周六,'' 周日 from temp group by to_char(createday,'yyyymm'),to_char(createday,'w')
谢谢
ZJHZ_叶 2019-07-18
  • 打赏
  • 举报
回复
是的,学习了
ZJHZ_叶 2019-07-17
  • 打赏
  • 举报
回复
引用 41 楼 nayi_224 的回复:
这么基础的groupby怎么连model都整出来了
with tab1 as (
select to_date('20190520', 'yyyymmdd') + level dt
from dual
connect by level <= 20
)
select min(t1.dt),
max(t1.dt)
from tab1 t1
group by to_char(t1.dt, 'mm'), to_char(t1.dt + 1, 'ww')
order by min(t1.dt)
;

你这个我前面写过了,to_char(,'w')/to_char(,'ww')并不是从周一开始的,而是当月(年)1-7号算一周,然后每7天算一周
nayi_224 2019-07-17
  • 打赏
  • 举报
回复
引用 42 楼 ZJHZ_叶 的回复:
[quote=引用 41 楼 nayi_224 的回复:]
这么基础的groupby怎么连model都整出来了
with tab1 as (
select to_date('20190520', 'yyyymmdd') + level dt
from dual
connect by level <= 20
)
select min(t1.dt),
max(t1.dt)
from tab1 t1
group by to_char(t1.dt, 'mm'), to_char(t1.dt + 1, 'ww')
order by min(t1.dt)
;

你这个我前面写过了,to_char(,'w')/to_char(,'ww')并不是从周一开始的,而是当月(年)1-7号算一周,然后每7天算一周
[/quote]
那就改成iw呗
nayi_224 2019-07-17
  • 打赏
  • 举报
回复
这么基础的groupby怎么连model都整出来了
with tab1 as (
select to_date('20190520', 'yyyymmdd') + level dt
  from dual
connect by level <= 20
)
select min(t1.dt),
       max(t1.dt)
  from tab1 t1
 group by to_char(t1.dt, 'mm'), to_char(t1.dt + 1, 'ww')
 order by min(t1.dt)
;
wildwolv 2019-07-16
  • 打赏
  • 举报
回复
wildwolv 2019-07-16
  • 打赏
  • 举报
回复
wildwolv 2019-07-16
  • 打赏
  • 举报
回复
SELECT A || '至' || b AS 区间 FROM ( SELECT A .MW, MIN (A .DT) AS A, MAX (A .DT) AS b FROM ( SELECT TO_CHAR (dt, 'yyyy-mm-dd') AS dt, TO_CHAR (dt, 'MM') || TO_CHAR (dt, 'W') AS MW FROM ( SELECT TRUNC (SYSDATE - 1 + ROWNUM - 30, 'dd') dt FROM dual CONNECT BY ROWNUM <= 30 ) ) A GROUP BY A .mw ORDER BY mw );
码匀 2019-07-15
  • 打赏
  • 举报
回复
with temp as( select trunc(sysdate)-level createday from dual connect by level<100 ) select substr(listagg (to_char(createday,'yyyy/mm/dd'),'-') WITHIN GROUP (ORDER BY createday),1,10)||'-' ||substr(listagg (to_char(createday,'yyyy/mm/dd'),'-') WITHIN GROUP (ORDER BY createday),-10,10) week ,'' 周一,'' 周二,'' 周三,'' 周四,'' 周五,'' 周六,'' 周日 from temp group by to_char(createday,'yyyymm'),to_char(createday,'w')
Yvette_QIU 2019-07-11
  • 打赏
  • 举报
回复
引用 34 楼 luj_1768的回复:
逻辑错误!当月最后一天是星期六或者星期日,怎么办?
哈?没有呀,先按周分,该月的最后一天刚好为周日,那就不需要再按月分了,若为周六的话,还是要按月分,一周就有两个时段:周一至周六、周日至周日(即周日零点零分零秒至周日23点59分59秒),,,,题目逻辑没有问题呀!你说哪里有问题,洗耳恭听
Yvette_QIU 2019-07-10
  • 打赏
  • 举报
回复
引用 28 楼 软件琪牌开发_Chen的回复:
666666666666
真的急用,,,后面自己尝试,实在菜,搞不定,还是得问问大神
IVDS2016 2019-07-10
  • 打赏
  • 举报
回复
希望有人能帮到你
ZJHZ_叶 2019-07-10
  • 打赏
  • 举报
回复
引用 27 楼 Yvette_QIU 的回复:
[quote=引用 26 楼 Yvette_QIU的回复:]我还有个问题,,,恕我愚钝,我若将查询条件传至这个SQL语句,在temp里如何改,如2019/05/28-2019/06/07起止日期

我觉得level就用不了了[/quote]


select
ROW_NUMBER() OVER(ORDER BY to_date('20190528','yyyymmdd')+level-1) RN,
to_char(to_date('20190528','yyyymmdd')+level-1,'yyyymm') createmonth,
to_date('20190528','yyyymmdd')+level-1 createday
from dual
connect by level<=to_date('20190607','yyyymmdd')-to_date('20190528','yyyymmdd')+1
加载更多回复(30)

17,140

社区成员

发帖
与我相关
我的任务
社区描述
Oracle开发相关技术讨论
社区管理员
  • 开发
  • Lucifer三思而后行
  • 卖水果的net
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧