我正在我的数据仓库中建立一个时间维度。我已经有了日期维度。
我如何表示未知时间?在我的DimDate维度中,我将01/01/1753标记为未知日期,但我认为时间会更难。我们的事实表中不允许使用NULL。我该怎么做,这行可能是什么样的?
您声明“我们不允许在事实表中使用NULL”,但询问“我如何表示未知时间?”
假设您在FACT表中使用数据类型TIME +对来自源系统的数据强制执行NOT NULL约束=>您根本无法将未知\无效时间插入到您的事实中,因此应该没有问题。
上面的一个明显的例外是源系统报告的商业智慧值无效,例如Sunil提出的('00:59:59.9999999'),但这是非常罕见的,不稳定的解决方案,出于明显的原因(不断变化的要求可以很容易地将这个值转化为一个有效的)
如果您选择允许(并且我希望您这样做)来自源系统的NULL值或无效日期的记录输入事实,那么最佳做法是在我们的DimTime上使用代理键并将它们作为FK插入到您的FACT表中 - 这您可以轻松地在维度中表示有效+无效值。这种方法也可以轻松地支持无效商业智能值('00:59:59.9999999')的方法,这样的值得到FK_DimTime = -1。
我强烈建议允许来自源系统的特定类型的垃圾进入FACT(即 - 无效\缺失\ NULL日期\时间值)表,只要您在相关的DIM中清楚地标记它,因为这往往会驱动用户提高数据质量在源系统中。
以下是关于https://www.kimballgroup.com/1997/07/its-time-for-time/ https://www.kimballgroup.com/2004/02/design-tip-51-latest-thinking-on-time-dimension-tables/问题的一些背景知识
它看起来像你想要的任何东西。大多数维度都有某种“显示名称”,因此您的尺寸可能如下所示:
create table dbo.DimDate (DateID int, DateValue date, DisplayDate nvarchar(20))
go
-- this is an unknown date; 1753-01-01 is only there because we need some valid date value
insert into dbo.DimDate values (1, '1753-01-01', 'Unknown')
go
-- this is the real date 1 Jan 1753
insert into dbo.DimDate values (2, '1753-01-01', '01 Jan 1753')
go
create table dbo.DimTime (TimeID int, TimeValue time, DisplayTime nvarchar(20))
go
-- this is an unknown time; 00:00 is only there because we need some valid time value
insert into dbo.DimTime values (1, '00:00', 'Unknown')
go
-- this is the real time value for midnight
insert into dbo.DimTime values (2, '00:00', 'Midnight')
go
当然,这假设您的报告工具和用户使用DisplayDate
和DisplayTime
列直接过滤而不是DateValue
和TimeValue
列,但这只是培训和标准的问题,无论如何您需要了解所采用的解决方案。
还有其他替代方法,例如未知值的标志列,或负TimeID
表示未知值的约定。但在我看来,这些不是明显的行值,也不是明确的行值。
只需使用DimTime
技术代理键创建-1
记录,并在时间列填充值'00:59:59.9999999
'。通过DWH,这将是一个不太可能的时间(精确到最后一位),当你想要过滤器时,它总是等于报告或查询中的未知时间,
EventTime < @ReportTime AND EventTime <> '00:59:59.9999999'
希望这是解决您问题的可行方案。