是否可以为每行数据存储历史配置设置,而不会将所有配置设置塞入每行数据?
Is it possible to store historical configuration settings for each row of data without cramming all the configuration settings into each row of data?
背景资料:我最近被一家水处理公司聘为数据库工程师。我们在全国各地部署水处理机,这些机器处理水并向我们发送有关进水状态(流速、温度、进水中 X 浓度等)的连续数据,以及有关处理的数据机器在那个时间点应用于该水。随着时间的推移,站点(及其各种组件)会发生很大变化:机器可能会发生故障并需要更换,可能会使用不同浓度的化学品来填充机器的水箱,其流量计和其他传感器可能会重新校准或设置为了以不同的方式扩大规模,它的化学泵可能会不断更换。这些会影响数据的解释:例如,如果在 2021 年 1 月 1 日 12:00:05 向进水中添加了 5 mL 氯,如果氯浓度为 5% 或 40%,则这意味着两种完全不同的情况集中.
水处理数据点由包含站点 ID 和时间戳的复合键标识。如果唯一重要的数据是当前数据,那将很容易,因为我可以将配置设置存储在站点级别,并根据需要将它们提取到数据点。但我们需要能够正确解释旧数据。因此,我考虑将配置存储在另一个 table 中,跟踪每个站点在每个时间段的所有设置,但是不可能在数据点的连续时间戳和 start/end 日期之间创建外键配置 - 最接近的是某种范围检查,例如“Datapoint.TimeStamp BETWEEN Configuration.Start AND Configuration.End”。因此,我看到的唯一其他选择是将每个数据点的每个配置设置与每个数据点一起存储,但考虑到有多少配置设置以及生成了多少数据点,这似乎是一个糟糕的解决方案,尤其是因为大多数设置都没有甚至经常改变。
那么,有没有办法以完全规范化的方式存储每行数据的历史配置,或者是将所有设置塞入每个数据点的唯一可能解决方案?
如果我理解你的要求:
1 - 水数据点由包含站点 ID 和时间戳的复合键标识:
- 站点 ID
- 时间戳ID
2 - 当发生故障时,水数据点可以有多种配置,例如:
- 配置ID
- 开始日期
- 结束日期
让我们考虑一个 DataPoint
具有特定日期的以下信息:
DataPoint SiteID TimeStampID
1001 101 01-02-2021 09:00:01
1001 101 01-02-2021 10:20:31
1001 101 01-02-2021 17:45:00
那天,故障开始于 11:01:20,结束于 11:34:22。
ConfigurationID DataPoint StartDate EndDate
155 1001 01-02-2021 11:01:20 01-02-2021 11:34:22
原来我接受的答案好像被删了。对于将来来到这里的任何人,我打算采用的解决方案如下:
我将创建一个配置 table 来保存以下格式的设置:
_SiteID_ _Start_ _End_ <various settings fields>
318 "2021-01-01 12:22:03" "2021-02-10 09:08:26" ...
其中主键是 (SiteID, Start, End)
。 SiteID
是Site
的整数ID
的外键table,Start
是配置开始生效的日期,End
(默认值:NULL
)是配置不再有效的日期。为了让用户(和我自己)保持良好和简单,并防止在本应插入新配置行时对旧配置设置进行任何意外更新,我将禁止 UPDATE
和 DELETE
对除 root 以外的所有用户的配置 table 操作,而是创建一个存储过程来“更新”给定 Site
的配置。存储过程将采用用户指定的任何新参数,复制用户未从该站点的最新配置中指定的任何参数(即具有相同 SiteID
和 [=17= 的行) ] 结束日期),将最近的配置行的 NULL
End
日期覆盖为新行的 Start
日期,最后创建具有指定 Start
的新行日期。
注意:Start
日期和End
日期都为每个配置存储,因为配置可能不一定是连续的,即它不是案例“一旦配置过期,就会有另一个配置在该配置过期的确切时间启动”,因为如果客户不需要我们的某些服务,水处理设备的部署有时会在它们之间有很大的差距一段的时间。如果不存储配置的 End
日期,我们将不得不假设每个配置持续到下一个配置开始,或者直到现在,如果没有存储以后的配置。因此 End
日期被存储,这样我们就不会认为“站点 A 被配置为具有从 2020 年 1 月到 2021 年 6 月的 X Y Z 设置”,而自 2020 年 5 月以来站点 A 甚至没有一台机器。将 End
日期明确地与 Start
日期一起存储也避免了需要依赖配置数据的其他行中的值来了解如何解释给定的配置数据行的麻烦。
感谢最初给了我这个答案灵感的人,我不知道为什么你的答案被删除了。
背景资料:我最近被一家水处理公司聘为数据库工程师。我们在全国各地部署水处理机,这些机器处理水并向我们发送有关进水状态(流速、温度、进水中 X 浓度等)的连续数据,以及有关处理的数据机器在那个时间点应用于该水。随着时间的推移,站点(及其各种组件)会发生很大变化:机器可能会发生故障并需要更换,可能会使用不同浓度的化学品来填充机器的水箱,其流量计和其他传感器可能会重新校准或设置为了以不同的方式扩大规模,它的化学泵可能会不断更换。这些会影响数据的解释:例如,如果在 2021 年 1 月 1 日 12:00:05 向进水中添加了 5 mL 氯,如果氯浓度为 5% 或 40%,则这意味着两种完全不同的情况集中.
水处理数据点由包含站点 ID 和时间戳的复合键标识。如果唯一重要的数据是当前数据,那将很容易,因为我可以将配置设置存储在站点级别,并根据需要将它们提取到数据点。但我们需要能够正确解释旧数据。因此,我考虑将配置存储在另一个 table 中,跟踪每个站点在每个时间段的所有设置,但是不可能在数据点的连续时间戳和 start/end 日期之间创建外键配置 - 最接近的是某种范围检查,例如“Datapoint.TimeStamp BETWEEN Configuration.Start AND Configuration.End”。因此,我看到的唯一其他选择是将每个数据点的每个配置设置与每个数据点一起存储,但考虑到有多少配置设置以及生成了多少数据点,这似乎是一个糟糕的解决方案,尤其是因为大多数设置都没有甚至经常改变。
那么,有没有办法以完全规范化的方式存储每行数据的历史配置,或者是将所有设置塞入每个数据点的唯一可能解决方案?
如果我理解你的要求:
1 - 水数据点由包含站点 ID 和时间戳的复合键标识:
- 站点 ID
- 时间戳ID
2 - 当发生故障时,水数据点可以有多种配置,例如:
- 配置ID
- 开始日期
- 结束日期
让我们考虑一个 DataPoint
具有特定日期的以下信息:
DataPoint SiteID TimeStampID
1001 101 01-02-2021 09:00:01
1001 101 01-02-2021 10:20:31
1001 101 01-02-2021 17:45:00
那天,故障开始于 11:01:20,结束于 11:34:22。
ConfigurationID DataPoint StartDate EndDate
155 1001 01-02-2021 11:01:20 01-02-2021 11:34:22
原来我接受的答案好像被删了。对于将来来到这里的任何人,我打算采用的解决方案如下:
我将创建一个配置 table 来保存以下格式的设置:
_SiteID_ _Start_ _End_ <various settings fields>
318 "2021-01-01 12:22:03" "2021-02-10 09:08:26" ...
其中主键是 (SiteID, Start, End)
。 SiteID
是Site
的整数ID
的外键table,Start
是配置开始生效的日期,End
(默认值:NULL
)是配置不再有效的日期。为了让用户(和我自己)保持良好和简单,并防止在本应插入新配置行时对旧配置设置进行任何意外更新,我将禁止 UPDATE
和 DELETE
对除 root 以外的所有用户的配置 table 操作,而是创建一个存储过程来“更新”给定 Site
的配置。存储过程将采用用户指定的任何新参数,复制用户未从该站点的最新配置中指定的任何参数(即具有相同 SiteID
和 [=17= 的行) ] 结束日期),将最近的配置行的 NULL
End
日期覆盖为新行的 Start
日期,最后创建具有指定 Start
的新行日期。
注意:Start
日期和End
日期都为每个配置存储,因为配置可能不一定是连续的,即它不是案例“一旦配置过期,就会有另一个配置在该配置过期的确切时间启动”,因为如果客户不需要我们的某些服务,水处理设备的部署有时会在它们之间有很大的差距一段的时间。如果不存储配置的 End
日期,我们将不得不假设每个配置持续到下一个配置开始,或者直到现在,如果没有存储以后的配置。因此 End
日期被存储,这样我们就不会认为“站点 A 被配置为具有从 2020 年 1 月到 2021 年 6 月的 X Y Z 设置”,而自 2020 年 5 月以来站点 A 甚至没有一台机器。将 End
日期明确地与 Start
日期一起存储也避免了需要依赖配置数据的其他行中的值来了解如何解释给定的配置数据行的麻烦。
感谢最初给了我这个答案灵感的人,我不知道为什么你的答案被删除了。