Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sql-server/27.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

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/email/3.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
sql server中两个日期之间的月份,以及sql server中每个日期的开始日期和结束日期_Sql_Sql Server_Date - Fatal编程技术网

sql server中两个日期之间的月份,以及sql server中每个日期的开始日期和结束日期

sql server中两个日期之间的月份,以及sql server中每个日期的开始日期和结束日期,sql,sql-server,date,Sql,Sql Server,Date,我想得到两个日期之间的月份及其开始和结束日期。假设我输入的起始日期为2017-04-01,结束日期为2017-07-31,我想得到月份列表,即分别为4月、5月、6月、7月及其开始和结束日期。请建议我如何实现 一种方法是递归CTE: with cte as ( select dateadd(day, 1 - day(@startdate), @startdate) as som, eomonth(@startdate) as eom union a

我想得到两个日期之间的月份及其开始和结束日期。假设我输入的起始日期为2017-04-01,结束日期为2017-07-31,我想得到月份列表,即分别为4月、5月、6月、7月及其开始和结束日期。请建议我如何实现

一种方法是递归CTE:

with cte as (
      select dateadd(day, 1 - day(@startdate), @startdate) as som,
             eomonth(@startdate) as eom
      union all
      select dateadd(month, 1, som), eomonth(dateadd(month, 1, som))
      from cte
      where dateadd(month, 1, som) < @enddate
     )
select *
from cte;
如果需要月份名称,则可以使用datenamemonth,som.

而不使用递归,使用master.dbo.spt_值替代数字表:

declare @StartDate date = '20170401'
      , @EndDate   date = '20170731';
;with Months as (
  select top (datediff(month,@startdate,@enddate)+1) 
      [Month] = dateadd(month, row_number() over (order by number) -1, @StartDate)
    , MonthEnd = dateadd(day,-1,dateadd(month, row_number() over (order by number), @StartDate))
  from master.dbo.spt_values
  order by [Month]
)
select * from Months;
rextester演示:

返回:

+------------+------------+
|   Month    |  MonthEnd  |
+------------+------------+
| 2017-04-01 | 2017-04-30 |
| 2017-05-01 | 2017-05-31 |
| 2017-06-01 | 2017-06-30 |
| 2017-07-01 | 2017-07-31 |
+------------+------------+
在SQL Server中生成集合或序列时,避免递归和循环的方法会随着值数量的增加而表现得更好

参考:

若要获取给定范围内每个月的开始和结束日期,@StartDate参数的值不是该月的第一天,请执行以下操作:

第一个选项是将@StartDate参数截断为月份的第一个,第二个选项是调整公共表表达式中的表达式以截断其中的值:

declare @StartDate date = '20170415'
      , @EndDate   date = '20170715';
/* Option 1: truncate @StartDate to the beginning of the month */
--set @StartDate = dateadd(month, datediff(month, 0, @StartDate), 0);
/* Option 2: Truncate @StartDate to month in the common table expression: */
;with Months as (
select top (datediff(month,@StartDate,@EndDate)+1) 
    [Month] = dateadd(month
               , datediff(month, 0, @StartDate) + row_number() over (order by number) -1
               , 0)
    , MonthEnd = dateadd(day,-1,dateadd(month
               , datediff(month, 0, @StartDate) + row_number() over (order by number) 
               ,0))
  from master.dbo.spt_values
  order by [Month]
)
select * from Months;
试试这个:

 DECLARE @Start DATE ='2017-04-01', 
        @End   DATE ='2017-07-31'


SELECT *, Datename(mm, date), 
       Dateadd(mm, Datediff(mm, 0, date), 0) AS FirstDateOfMonth, 
       Dateadd (dd, -1, Dateadd(mm, Datediff(mm, 0, date) + 1, 0)) as 
      LastDateOfMonth
FROM   dbo.TableName
WHERE  Cast(date AS DATE) BETWEEN @Start AND @End 

我为此创建了一个存储过程,您可以将其转换为用户定义的函数。 在下面发布代码

create procedure ListMonths
@date1 date,@date2 date 
as
begin
create Table #tempTable
(mnth varchar(10))
while @date1<@date2
begin
insert into #tempTable
select DATENAME(month,@date1)
set @date1 = DATEADD(MONTH,1,@date1)
end
select * from #tempTable;
drop table #tempTable;
end
输出

+------------+
|   mnth     |
+------------+
| April      |
| May        | 
| June       |
| July       |
| August     |
| September  |
| October    |
| November   |
| December   |
| January    |
+------------+
给你

创建模式

   create table abc(
      date1 date
    )

//Inserting data into it
    insert into abc values(getdate()), 
    (DATEADD(Month, -1, getdate())),
    (DATEADD(Month, -2, getdate())),
    (DATEADD(Month, -3, getdate())), 
    (DATEADD(Month, -4, getdate()))
最后,选择查询以获取开始日期和结束日期之间的数据:

select (datename(Month, date1)+' '+convert(varchar(2), date1, 103)) as [Date] from abc 
where convert(varchar(10), date1, 120) between '2017-05-02' and '2017-07-02'
获取两个日期之间数据的另一种方法:

select (datename(Month, date1)+' '+convert(varchar(2), date1, 103)) as [Date] from abc
where date1 >= (DATEADD(Month, -3, getdate())) AND date1 <=getdate();
返回的结果是:

这是可以测试此查询的小提琴->
简单易用…祝你好运兄弟:

如果这不仅仅是一份一次性报告,那么我会创建一个日历表,并使用它来分组。这还可以让您进行许多其他与日期相关的计算。 你可以在或在这里找到一个

那么您的代码可能如下所示:

SELECT top 10000 * FROM dbo.calendar DD
WHERE DD.TimeStampFrom>='2017-04-01' AND DD.TimeStampFrom <='2017-07-31'
AND DAY(DD.TimeStampFrom)=1

eom?应该是eomonth@NenadZivkovic . . . 谢谢。注意:支持从SQL Server开始2012@avinashss很乐意帮忙@SqlZim…如果我将开始日期设置为“2017-04-15”,将结束日期设置为“2017-07-15”,而将开始日期设置为“2017-07-15”,那么如何获得上述相同的结果,我想得到我想要的月份的第一个日期和最后一个日期get@avinashss我已经更新了我的答案,以显示当@StartDate的给定值不是该月的第一个月时,如何获得该月的开始和结束。请在包含代码的每行开始处添加4个空格。您也可以通过单击/拖动并单击{}按钮来选择它可能的副本
SELECT top 10000 * FROM dbo.calendar DD
WHERE DD.TimeStampFrom>='2017-04-01' AND DD.TimeStampFrom <='2017-07-31'
AND DAY(DD.TimeStampFrom)=1