我无法理解这段代码。它实际上似乎工作,但我不明白活动年和月的正确值如何“找到”得到适当的最小和最大?或者它是否运行所有排列最高?这对我来说很奇怪。
我确实理解dateadd是如何工作的,而不是查询实际上是如何工作的。这可能是一个糟糕的问题,因为我实际上并不需要帮助解决问题,只是深入了解其工作原理。
select
EmployeeNumber,
sum(BaseCalculation) as BaseCalculation,
min(dateadd(mm, (ActivityYear - 1900) * 12 + ActivityMonth - 1 , 0)) as StartDate,
max(dateadd(mm, (ActivityYear - 1900) * 12 + ActivityMonth - 1 , 0)) as EndDate
from
Compensation
where
1=1
-- and
group by
EmployeeNumber
答案 0 :(得分:0)
它将列ActivityYear
和ActivityMmonth
转换为日期。它是通过计算自1900年以来的月数并将它们添加到零时间来实现的。因此,2000年1月将变成像Jan,100这样的事情。这看起来像是一个非常神秘的计算,因为大约2000年的日期并不是真的有用。
当然,这假设ActivityYear
是近年来可识别的。
我会将年份和月份转换为月初的第一天,如下所示:
min(cast(cast(ActivityYear * 10000 + ActivityMonth + 1 as varchar(255)) as date)
答案 1 :(得分:0)
Sql Server将计算该语句的每个值,然后仅返回最小值和最大值
虽然我不能肯定地说sql server在内部以这种方式执行,但我想到它的方式我想象引擎剥离组和所有聚合函数,运行该查询。然后只需总结/找到最小值等。
答案 2 :(得分:0)
对于min
和max
函数调用,算法
dateadd(mm, (ActivityYear - 1900) * 12 + ActivityMonth - 1 , 0)
您的查询使用此算法从Compensation
表计算所有可能的日期。然后,您选择最短日期为StartDate
,最大日期为EndDate
。
这是返回正确的最大值和最小值的方式。
请注意,dateadd签名为DATEADD (datepart , number , date )
由于最后一个参数为0,因此您可以将月份(mm)添加到算法中计算的数字中,并返回从0开始的相应日期。
查看此信息以获取更多信息:https://msdn.microsoft.com/en-us/library/ms186819.aspx