3

我想正确设计我的数据库。也许有人可以帮助我。

我有一个设备,它每 3 秒将大约 100 个键/值写入一个表。有人建议这样存储:

^ 时间戳 ^ key1 ^ key2 ^ [...] ^ key150 ^

| 2012 年 12 月 6 日 | 空 | 2243466 | [...] | 空^

但我认为那是完全错误的,不是动态的。因为我可以有很多空值。所以我尽力做到最好,并按照我在学校的学习方式设计它:http: //ondras.zarovi.cz/sql/demo/?keyword= tempidi

这是我为每个值编写时间戳的问题,这意味着在 100 个值内它将始终相同并产生大量数据。

有人可以给我提示如何减小数据库大小吗?我的 ERM 基本上是正确的吗?

4

2 回答 2

1

我不会太担心数据库的大小。您更大的问题是维护和灵活性。

这就是我要做的。首先,使用您的设备可以编写的可能键定义并填充此表:

tblDataKey
(
    ID int primary key (auto-increment - not sure how mysql does this)
    Name varchar(32)
)

接下来定义一个“数据事件”表:

tblEvent
(
    ID int primary key (auto-inc)
    TimeStamp
    ...anything else you need - device ID's? ...
)

然后将事件与键及其值匹配:

tblEventData
{
    EventID INT FK-to-tblEvent
    KeyID INT FK-to-tblDataKey
    DataValue varchar(???)
)

现在,无论多少秒,您的数据都会在 tblEvent 中创建一个条目,并在 tblEventData 中创建多个条目,并根据需要使用键值。并非每个事件都需要每个键,将来您可以扩展键的数量。

这真的很闪耀,因为空间没有被浪费,您可以轻松地使用特定的数据键和值对 evnet 进行查询。当您需要生成事件和数据项的“交叉表式”表时,这种结构就会失败。你必须决定这是否有问题。

于 2012-12-06T18:51:28.980 回答
0

如果你必须在 MySQL 中实现一个键值对存储,让它比这更复杂是没有任何意义的。

create table key_value_store (
  run_time datetime not null,
  key_name varchar(15) not null,
  key_value varchar(15) not null,
  primary key (run_time, key_name)
);

如果您的键和值的平均长度都是 10 字节,那么您每月查看大约 8600 万行和 2.5GB,并且您不需要任何连接。如果所有值(列 key_value)都是整数或浮点数,则可以更改数据类型并进一步减少空间。

在 SQL 中实现键值存储的主要问题之一是,除非所有值都是相同的数据类型,否则您必须对所有值使用类似 varchar(n) 的东西。你失去了类型安全和声明性约束。(您无法检查 key3 的值是否在 1 和 15 之间,而 key7 的值在 0 和 3 之间。)


这可行吗?

这种结构(称为“EAV”--Google 认为)是一种众所周知的表格设计反模式。部分问题在于您实际上是将列存储为行。(您将列名存储在 key_value_store.key_name 中。)如果您必须以普通表的格式写出数据,您会发现三件事。

  1. 很难编写查询以输出正确的格式。
  2. 它需要永远运行。如果您必须编写数百列,它可能永远无法完成。
  3. 你会希望你有更快的硬件。快得多硬件。

我在寻找什么

  • 将键分组到逻辑表中的机会。这与第一个设计有关,它可能不适用于您。听起来您的应用程序基本上是在存储一个日志文件,并且您不知道每次运行时哪些键将具有值。
  • 减少行数的机会。我会问,“我们能不能少写点?” 因此,我会考虑每 5 或 6 秒而不是每 3 秒写入一次数据库,假设这意味着我正在写入更少的行。(真正的目标是更少的行,而不是更少的写入。)
  • 合适的平台。PostgreSQL 9.2 可能是一个更好的选择。9.2 版具有仅索引扫描,并且具有实现键值存储的 hstore 模块。

在你决定之前测试

如果我站在你的立场上,我会在 MySQL 和 PostgreSQL 中构建这个表。我会用大约一百万行随机数据加载每个。然后我会尝试一些查询和报告。(报告很重要。)衡量绩效。将负载增加到 1000 万行,重新调整服务器和 dbms,然后再次运行相同的查询和报告。再次测量。

重复 1 亿行。当你有信心时退出。预计这一切需要几天时间。

于 2012-12-06T19:20:52.023 回答