Mysql Timeserie数据库线性存储

Mysql Timeserie数据库线性存储,mysql,database,time-series,Mysql,Database,Time Series,我想将时间序列存储在MySQL数据库中。我想以线性的方式来做,也就是说,每一行代表一个唯一的观察(1个度量值,1个站点,1个时间戳)。目前,它将需要84096000行行,每年将增长约2102400行 为了正确设计时间序列表、索引和相关查询(基本上是确定度量、地点和时间范围的数据选择),必须采取哪些预防措施 编辑: 增加一个表格设计方案: CREATE TABLE TimeSeries( Id INT NOT NULL AUTO_I

我想将时间序列存储在MySQL数据库中。我想以线性的方式来做,也就是说,每一行代表一个唯一的观察(1个度量值,1个站点,1个时间戳)。目前,它将需要
84096000行
行,每年将增长约
2102400行

为了正确设计时间序列表、索引和相关查询(基本上是确定度量、地点和时间范围的数据选择),必须采取哪些预防措施

编辑:

增加一个表格设计方案:

CREATE TABLE TimeSeries(
   Id                  INT          NOT NULL     AUTO_INCREMENT,
   MeasureTimeStamp    DATETIME     NOT NULL, 
   MeasureId           INT          NOT NULL,
   SiteId              INT          NOT NULL,
   Measure             FLOAT        NOT NULL,
   Quality             INT          NOT NULL,   
   PRIMARY KEY (Id),
   CONSTRAINT UNIQUE (MeasureTimeStamp,MeasureId,SiteId),
   FOREIGN KEY (MeasureId) REFERENCES Measure(Id),
   FOREIGN KEY (SiteId) REFERENCES Site(Id)
);
CREATE INDEX ChannelIndex ON TimeSeries(MeasureId,SiteId);
如果存在度量值和站点表,如果我的主要问题是:

SELECT *
FROM TimeSeries
WHERE (MeasureId IN (?,?,?)) 
  AND (SiteId IN (?,?,?))
  AND (MeasureTimeStamp BETWEEN ? AND ?)
ORDER BY MeasureId ASC,
         SiteId ASC,
         MeasureTimeStamp ASC;
编辑2:

场地约20个,措施约50个。这将导致最多1000个通道(一对站点和测量)。它可能会在几十年内略有增加,但不会超过10000个频道。大多数数据的时间颗粒度约为30分钟。无论如何,时间颗粒度不是常数,不会小于一分钟(有些数据是每天或每周的)。

一些线索:

  • MySQL中的索引是按“索引列”排序的主键列表。您希望对列表进行排序,以便尽可能容易地找到所需的值
  • MySQL一次只在一个表上使用一个索引
  • MySQL可以使用从左到右的索引()。这意味着索引(A,B,C)允许您执行
    其中A=?和B=?
    但不是
    ,其中B=?和C=?
在您的示例中,创建了四个索引:

  • MeasureId,SiteId
    (ChannelIndex)
  • MeasureTimeStamp、MeasureId、SiteId
    (唯一约束)
  • MeasureId
    (外键)
  • SiteId
    (外键)
简单地说,ChannelIndex的排序类似于结合MeasureId和SiteId的字符串列表。例如,对于MeasureId=12和Site Id=68,您可以将排序值想象为
12_68
。 您的唯一约束根据值进行排序,如
2014-12-23 09:01:43_12_68

为了解决您的查询,MySQL可以使用您的索引或唯一约束。这取决于它选择的表中的数据。然而,两者都不是最优的。使用索引,它将在索引中快速找到具有正确的
MeasureId
SiteId
的块,但随后需要进入主表中的每个值,以检查
MeasureTimeStamp
是否在范围内。 使用唯一约束,它可以轻松地选择时间范围。然而,该索引子集具有随机排序的
MeasureId
SiteId
,仍然由MeasureTimeStamp排序

为了改进结构,将唯一约束更改为

约束唯一(MeasureId、SiteId、MeasureTimeStamp)


该索引现在将使用
12\u 68\u 2014-12-23 09:01:43
这样的值进行排序,我希望它能显示更好的性能,因为MySQL现在可以在索引中选择离散和可预测的范围数。这覆盖了SELECT语句,同时使索引变得多余。

MySQL可以轻松处理它。您期望哪种类型的WHERE子句?至少,“site”的索引。
WHERE
子句将至少选择两个以上的外键
site
,并使用
列表标准中的
(这些列当然将被索引)和
时间戳
之间的
(索引是因为它是主键的一部分)然后我建议用
site
measure
建立一个索引。这两列将减少足够多的结果,以提高效率。如果在混合中添加时间戳,则索引的行数将与数据表的行数相同,MySQL将忽略它。与实际每秒写入操作数(包括FKs)相比,您的年增长率没有那么令人担忧。你能多谈谈数据的“密度”吗。。。有5个站点吗?还是五万?有多少措施?是否每秒记录TS,每秒10次?等@cerd增加了关于FK密度的精度