Cal*_*der 14 database-design sql-server
我目前的任务是为相对大量的数据实施存储模式。将主要访问数据以确定当前data point值,但我还需要跟踪过去六个月的历史数据趋势/分析。
加入最近要求跟踪min/ max/sum在过去的小时值。
注意:理想情况下,我想考虑 MongoDB 选项,但我需要先证明我已经用完了 SQL-Server 选项。
数据
下表表示主要数据源(最常查询)。该表将有大约 500 万行。数据更改将主要是初始数据加载后UPDATE非常偶然的INSERT语句。我选择了对数据进行聚类,dataPointId因为您将始终选择all values for a given data point.
// Simplified Table
CREATE TABLE [dbo].[DataPointValue](
[dataPointId] [int] NOT NULL,
[valueId] [int] NOT NULL,
[timestamp] [datetime] NOT NULL,
[minimum] [decimal](18, 0) NOT NULL,
[hourMinimum] [decimal](18, 0) NOT NULL,
[current] [decimal](18, 0) NOT NULL,
[currentTrend] [decimal](18, 0) NOT NULL,
[hourMaximum] [decimal](18, 0) NOT NULL,
[maximum] [decimal](18, 0) NOT NULL
CONSTRAINT [PK_MeterDataPointValue] PRIMARY KEY CLUSTERED ([dataPointId],[valueId])
)
Run Code Online (Sandbox Code Playgroud)
第二个表明显更大,大约有 31 亿行(代表过去六个月的数据)。超过六个月的数据将被清除;否则严格的数据INSERT语句(~200 行/秒,720,000 行/小时,1700 万行/周)。
// Simplified Table
CREATE TABLE [dbo].[DataPointValueHistory](
[dataPointId] [int] NOT NULL,
[valueId] [int] NOT NULL,
[timestamp] [datetime] NOT NULL,
[value] [decimal](18, 0) NOT NULL,
[delta] [decimal](18, 0) NOT NULL
CONSTRAINT [PK_MeterDataPointHistory] PRIMARY KEY CLUSTERED ([dataPointId], [valueId], [timestamp])
Run Code Online (Sandbox Code Playgroud)
)
预期随着跟踪数据点值的数量增加到 400 行/秒(因此达到 ~ 100 亿并非不可能),该表的大小将增加一倍。
问题(是的,我问的不止一个……它们都密切相关)。
我目前使用的是 SQL-Server 2008 R2 标准版数据库。如果可以通过表分区获得所需的性能级别(或 MongoDB,如果无法使用 SQL-Server 达到所需的性能级别),我可能会考虑升级到企业版。我希望您对以下内容提出意见:
1) 鉴于我需要计算过去一小时的min,max和sum(如now - 60 minutes)。跟踪最近数据的最佳方法是什么:
将最近的数据保存在数据服务的内存中。用每个数据更新写出计算的最小值/最大值/平均值。
在每个 UPDATE 语句期间从历史记录表中查询最近的历史记录(影响下一个问题?)。查询将访问数据点值的最新数据,并且应该只扫描最后一百万条记录左右?
将最近的历史记录存储在 DataPointValue 行本身以避免历史表查找?也许存储为分隔字符串并在 UPDATE 过程中处理?
我还没有考虑过的其他选择?
2) 对于DataPointValueHistory,对数据的查询将始终由dataPointId和 一个或多个valueId's 进行。查询的数据通常是最后一天、一周或一个月的数据,但在某些情况下可能是整整六个月。
我目前正在生成一个示例数据集,以试验按 dataPointId/valueId/timeStamp 或 timeStamp/dataPointId/valueId 进行聚类是否更有意义。如果有人有处理这种尺寸的桌子的经验并愿意提供他们的见解,我们将不胜感激。我倾向于后一种选择以避免索引碎片,但查询性能至关重要。
集群DataPointValueHistory由dataPointId - > VALUEID - >的timeStamp
集群DataPointValueHistory通过时间戳- > dataPointId - > VALUEID
3)最后,如上所述,我认为对DataPointValueHistory表进行分区是有意义的。任何关于如何最好地划分历史数据的建议将不胜感激。
如果首先按时间戳聚类,我认为数据应该按周进行分区(总共 27 个分区)。最早的分区将在第 27 周后被清除。
如果首先按 dataPointId 聚类,我认为数据应该按 id 的某个模数进行分区?
由于我在表分区方面的经验非常有限,您的专业知识将不胜感激。
| 归档时间: |
|
| 查看次数: |
25084 次 |
| 最近记录: |