Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/date/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Postgresql 如何在Postgress中获得给定月份的周范围_Postgresql_Date - Fatal编程技术网

Postgresql 如何在Postgress中获得给定月份的周范围

Postgresql 如何在Postgress中获得给定月份的周范围,postgresql,date,Postgresql,Date,这是我当前的实施方案 SELECT date_trunc('month', do_date::date)::date as starting_of_the_month, (date_trunc('month', do_date::date) + interval '1 month' - interval '1 day')::date as ending_of_the_month, case when 1 + FLOOR((EXTRACT(DAY FROM do_da

这是我当前的实施方案

SELECT

    date_trunc('month', do_date::date)::date as starting_of_the_month,

    (date_trunc('month', do_date::date) + interval '1 month' - interval '1 day')::date as ending_of_the_month,

    case when 1 + FLOOR((EXTRACT(DAY FROM do_date) - 1) / 7) = 1
        THEN date_trunc('week', do_date)::date || ' - ' ||
                  (date_trunc('week', do_date) + '6 days') ::date end as week1,
    case when 1 + FLOOR((EXTRACT(DAY FROM do_date) - 1) / 7) = 2
             THEN date_trunc('week', do_date)::date || ' - ' ||
                  (date_trunc('week', do_date) + '6 days') ::date end as week2,
    case when 1 + FLOOR((EXTRACT(DAY FROM do_date) - 1) / 7) = 3
             THEN date_trunc('week', do_date)::date || ' - ' ||
                  (date_trunc('week', do_date) + '6 days') ::date end as week3,
    case when 1 + FLOOR((EXTRACT(DAY FROM do_date) - 1) / 7) = 4
             THEN date_trunc('week', do_date)::date || ' - ' ||
                  (date_trunc('week', do_date) + '6 days') ::date end as week4,
    case when 1 + FLOOR((EXTRACT(DAY FROM do_date) - 1) / 7) = 5
             THEN date_trunc('week', do_date)::date || ' - ' ||
                  (date_trunc('week', do_date) + '6 days') ::date end as week5

FROM sales_dos

WHERE date_trunc('month', do_date::date)::date >= '2021-02-01' AND date_trunc('month', do_date::date)::date <  '2021-02-28'

选择
日期(“月”,执行日期::日期)::作为该月开始日期的日期,
(日期(“月”,日期::日期)+间隔“1个月”-间隔“1天”)::日期为该月的结束日期,
1+楼层((提取(从开工日期算起的日期)-1)/7)=1时的情况
然后date|trunc('week',do|date)::date | |'-'||
(日期(“周”,完成日期)+“6天”):日期结束为第1周,
1+楼层((摘录(从开工日期算起的日期)-1)/7)=2时的情况
然后date|trunc('week',do|date)::date | |'-'||
(日期(“周”,完成日期)+“6天”):日期结束为第2周,
1+楼层时的情况(摘录(从开工日期算起的日期)-1)/7)=3
然后date|trunc('week',do|date)::date | |'-'||
(日期(“周”,完成日期)+“6天”):日期结束为第3周,
1+楼层时的情况((摘录(从开工日期算起的日期)-1)/7)=4
然后date|trunc('week',do|date)::date | |'-'||
(日期(“周”,完成日期)+“6天”):日期结束为第4周,
1+楼层时的情况(摘录(从开工日期算起的日期)-1)/7)=5
然后date|trunc('week',do|date)::date | |'-'||
(日期(“周”,完成日期)+“6天”):日期结束为第5周
来自销售部
其中日期(“月”,执行日期::日期)::日期>='2021-02-01'和日期(“月”,执行日期::日期)::日期<'2021-02-28'
这是我目前的输出:

我希望输出显示如下:

第一周:2021-02-01-2021-02-07

第2周:2021-02-08-2021-02-14

第3周:2021-02-15-2021-02-21

第4周:2021-02-22-2021-02-28


第5周:-

我首先要简化为:

extract(day from do_date)::int / 7 + 1 as week_in_month

然后,使用该方法进行重点分析。

我将首先简化为:

extract(day from do_date)::int / 7 + 1 as week_in_month

然后使用。

将重点放在使用标准日历的混合ISO上。您正在使用ISO周的开始和结束时间,但不是所有周都是7天,而是可能会截断第一周和/或最后一周

这方面的需求变化实际上并不广泛。对于初始查询,返回ISO周的开始日期,而不是当月的第一天。然后,主查询检查第1周,如果是,则生成该月的第1周。唯一的问题是确定ISO周开始日期。为此,我刚刚加入了一个函数,我已经为此专门使用了一段时间。对week_days函数的更改被标记为--,因此您需要的是一个带有标准日历的混合ISO。您正在使用ISO周的开始和结束时间,但不是所有周都是7天,而是可能会截断第一周和/或最后一周

这方面的需求变化实际上并不广泛。对于初始查询,返回ISO周的开始日期,而不是当月的第一天。然后,主查询检查第1周,如果是,则生成该月的第1周。唯一的问题是确定ISO周开始日期。为此,我刚刚加入了一个函数,我已经为此专门使用了一段时间。对week_days函数的更改被标记--这里是另一种方法(例如2021年1月)

与
t as(选择日期(“月”,“2021-03-11”::日期)为今天),即2021年1月的任何日期
s作为
(
选择d::date,d::date+6 ed,从d中提取('isodow')wd
从t开始,生成_序列(每天,每天+间隔“1个月-1天”,间隔“1天”)d
)
选择格式('Week%s',extract(从d开始的日期)::integer/7+1)作为weekname、d、ed
从s
其中wd=1;

这里是另一种方法(例如2021年1月)

与
t as(选择日期(“月”,“2021-03-11”::日期)为今天),即2021年1月的任何日期
s作为
(
选择d::date,d::date+6 ed,从d中提取('isodow')wd
从t开始,生成_序列(每天,每天+间隔“1个月-1天”,间隔“1天”)d
)
选择格式('Week%s',extract(从d开始的日期)::integer/7+1)作为weekname、d、ed
从s
其中wd=1;

请参见@Bohemian修改答案和/或答案。在2021年4月测试时,此查询输出的周范围不正确,例如:('2021-04-23')。您需要指定预期结果,并正确定义周的含义。从您的样本数据推断,本月的第1周从本月的第1天开始,为期7天,除最后一周在本月的最后一天结束外,每周都是如此。这正是查询为2021年4月生成的结果。很抱歉没有详细说明问题,是的,实际上我需要一个月的周初从该月的开始日期开始,到周日结束。与2021年4月一样,第1周应为(01-04-2021至04-04-2021)、第2周(05-04-2021至11-04-2021)和第5周(26-04-2021至30-04-2021),请参见修订答案。请参见@Bohemian修改答案和/或答案。在2021年4月测试时,此查询输出的周范围不正确,例如:('2021-04-23')。您需要指定预期结果,也要正确定义你所说的周。从您的样本数据推断,本月的第1周从本月的第1天开始,为期7天,除最后一周在本月的最后一天结束外,每周都是如此。这正是查询为2021年4月生成的结果。很抱歉没有详细说明问题,是的,实际上我需要一个月的周初从该月的开始日期开始,到周日结束。与2021年4月一样,第1周应为(01-04-2021至04-04-2021)、第2周(05-04-2021至11-04-2021)和第5周(26-04-2021至30-04-2021),请参见修订后的答案。在2019年3月进行尝试时,此查询给出的周数不正确。第1周的预期输出应为2019年3月1日至2019年3月3日,但此查询给出的第1周结果为2019年3月4日至2019年3月10日。此查询在重试时给出的周数不正确
create or replace 
function week_dates( do_date_in date) 
 returns table (ween_num integer, first_date date, last_date date)
 language sql 
 immutable strict
as $$
    with recursive date_list(week_num,first_date,terminate_date) as 
         ( select 1
                , date_trunc('month', do_date_in)::timestamp
                , (date_trunc('month', do_date_in) + interval '1 month' - interval '1 day')::timestamp
           union all 
           select week_num+1, (first_date+interval '7 day'), terminate_date
             from date_list
            where first_date+interval '6 day'  < terminate_date::timestamp    
         ) 
    select week_num
         , first_date::date
         , case when (first_date+interval '6 day')::date > terminate_date 
                then terminate_date::date 
                else (first_date+interval '6 day')::date 
           end last_date
    from date_list;
$$; 
 
select week1s  
     , case when week5e is null 
            then week4e
            else week5e
       end "end of month"
     , week1s  || ' -  ' || week1e  
     , week2s  || ' -  ' || week2e  
     , week3s  || ' -  ' || week3e  
     , week4s  || ' -  ' || week4e  
     , week5s  || ' -  ' || week5e  
  from ( select  max(case when (week_num=1) then first_date else NULL end) as week1s 
              ,  max(case when (week_num=1) then last_date  else NULL end) as week1e         
              ,  max(case when (week_num=2) then first_date else NULL end) as week2s
              ,  max(case when (week_num=2) then last_date  else NULL end) as week2e      
              ,  max(case when (week_num=3) then first_date else NULL end) as week3s
              ,  max(case when (week_num=3) then last_date  else NULL end) as week3e      
              ,  max(case when (week_num=4) then first_date else NULL end) as week4s
              ,  max(case when (week_num=4) then last_date  else NULL end) as week4e      
              ,  max(case when (week_num=5) then first_date else NULL end) as week5s
              ,  max(case when (week_num=5) then last_date  else NULL end) as week5e      
           from week_dates(current_date)
        ) w ;