到底什么是广列存储?

79

在谷歌上搜索“wide column stores” 的定义,会得到列式数据库的结果,或者是非常模糊的定义。

我的理解是,宽列存储由列族组成,列族中包含行和列。该族中的每一行都一起存储在磁盘上。这听起来像是行式数据库存储数据的方式。这就带来了我的第一个问题:

宽列存储与普通关系型数据库表有何不同? 我的看法如下:

* column family        -> table
* column family column -> table column
* column family row    -> table row

这张来自《数据库内部原理》的图片看起来就像两个普通的表格: 两个列族、内容和锚点 我猜想不同的地方在于“多维地图”与广列存储并提到了。所以这是我的第二个问题:
广列存储是否从左往右排序?也就是说,在上面的示例中,行首先按行键排序,然后按时间戳排序,最后按修饰符排序?

1
什么是宽列数据库?https://www.dataversity.net/wide-column-database/# - Gilbert Le Blanc
5
我认为这与其他在线定义一样存在问题,它简短而模糊:“其体系结构使用持久的、稀疏矩阵、多维映射(行值、列值和时间戳)以表格格式进行大规模可扩展性设计(超过PB级别)。列族存储不遵循关系模型,也没有针对联接进行优化。”我意识到,如果您已经了解列式存储,这可能已足够。但是,如果您还不了解,这并不能帮助建立心理模型。毕竟,BigTable的论文长达14页。 - Moo
2
顺便说一句,我读了BigTable论文的前两页,它实际上有一个最好的广列存储解释器之一。建议任何人都去尝试一下。 - Moo
2个回答

75
让我们从广列数据库的定义开始。
其架构使用(a)持久性、稀疏矩阵、多维映射(行值、列值和时间戳)以表格格式表示,旨在实现超大规模的可扩展性(超过PB级别)。
关系型数据库旨在维护实体与描述实体的列之间的关系。一个很好的例子是客户表。这些列包含描述客户姓名、地址和联系信息的值。所有这些信息对于每个客户都是相同的。
广列数据库是NoSQL数据库的一种类型。
也许这是四个广列数据库更好的形象。

Wide column databases

我理解的是,顶部的第一张图片,列模型,是我们所称的实体/属性/值表。它是特定实体(列)中的属性/值表。

对于客户信息,第一个广域数据库示例可能如下所示。

Customer ID    Attribute    Value
-----------    ---------    ---------------
     100001    name         John Smith
     100001    address 1    10 Victory Lane
     100001    address 3    Pittsburgh, PA  15120

是的,我们可以为关系型数据库建模。属性/值表的强大之处在于更不寻常的属性。

Customer ID    Attribute    Value
-----------    ---------    ---------------
     100001    fav color    blue
     100001    fav shirt    golf shirt

任何营销人员能够想象到的属性都可以被捕获并存储在属性/值表中。不同的客户可能有不同的属性。

超级列模型以不同的格式保留相同的信息。

Customer ID: 100001
Attribute    Value
---------    --------------
fav color    blue
fav shirt    golf shirt

您可以拥有与实体数量相同的超级列模型。它们可以在单独的NoSQL表中或作为超级列族放在一起。

列族和超级列族仅仅为图片中前两个模型分配一个行ID,以便更快地检索信息。


3
谢谢您提供更详细的回复! - Moo
非常感谢你的出色回答。你提供的例子和与EAV的链接真正让我理解了这个概念。 - Ed Graham
谢谢您的详细回答;我发现这篇文章(https://dandkim.com/wide-column-databases/)对于这个问题是一个有用的补充资源。 - sam-6174
我们可以说宽列(wide column)类似于 Excel 如何存储数据吗?你也可以在其中创建超级列。除了使用较小的表/列作为更大的表中的模块的这个功能之外,我没有看到任何其他独特的“宽列”功能。请问我的理解正确吗? - A B

11

大多数(如果不是全部)宽列存储实际上都是面向行的存储方式,即记录的所有部分都存储在一起。你可以将其看作是一个二维键值存储。键的第一个部分用于在服务器之间分配数据,键的第二个部分让你快速在目标服务器上找到数据。

不同的宽列存储会有不同的特性和行为。然而,例如Apache Cassandra允许你定义数据的排序方式。以这个表格为例:

| id | country | timestamp  | message |
|----+---------+------------+---------|
| 1  | US      | 2020-10-01 | "a..."  |
| 1  | JP      | 2020-11-01 | "b..."  |
| 1  | US      | 2020-09-01 | "c..."  |
| 2  | CA      | 2020-10-01 | "d..."  |
| 2  | CA      | 2019-10-01 | "e..."  |
| 2  | CA      | 2020-11-01 | "f..."  |
| 3  | GB      | 2020-09-01 | "g..."  |
| 3  | GB      | 2020-09-02 | "h..."  |
|----+---------+------------+---------|

如果您的分区键是(id),并且您的聚簇键是(country, timestamp),则数据将存储如下:
[Key 1]
1:JP,2020-11-01,"b..." | 1:US,2020-09-01,"c..." | 1:US,2020-10-01,"a..."
[Key2]
2:CA,2019-10-01,"e..." | 2:CA,2020-10-01,"d..." | 2:CA,2020-11-01,"f..."
[Key3]
3:GB,2020-09-01,"g..." | 3:GB,2020-09-02,"h..."

或者以表格形式:

| id | country | timestamp  | message |
|----+---------+------------+---------|
| 1  | JP      | 2020-11-01 | "b..."  |
| 1  | US      | 2020-09-01 | "c..."  |
| 1  | US      | 2020-10-01 | "a..."  |
| 2  | CA      | 2019-10-01 | "e..."  |
| 2  | CA      | 2020-10-01 | "d..."  |
| 2  | CA      | 2020-11-01 | "f..."  |
| 3  | GB      | 2020-09-01 | "g..."  |
| 3  | GB      | 2020-09-02 | "h..."  |
|----+---------+------------+---------|

如果你将主键(分区键和聚簇键的组合)更改为(id,timestamp) WITH CLUSTERING ORDER BY(timestamp DESC)(其中 id 是分区键,timestamp 是按降序排列的聚簇键),则结果将如下:

[Key 1]
1:US,2020-09-01,"c..." | 1:US,2020-10-01,"a..." | 1:JP,2020-11-01,"b..." 
[Key2]
2:CA,2019-10-01,"e..." | 2:CA,2020-10-01,"d..." | 2:CA,2020-11-01,"f..."
[Key3]
3:GB,2020-09-01,"g..." | 3:GB,2020-09-02,"h..."

或以表格形式呈现:

| id | country | timestamp  | message |
|----+---------+------------+---------|
| 1  | US      | 2020-09-01 | "c..."  |
| 1  | US      | 2020-10-01 | "a..."  |
| 1  | JP      | 2020-11-01 | "b..."  |
| 2  | CA      | 2019-10-01 | "e..."  |
| 2  | CA      | 2020-10-01 | "d..."  |
| 2  | CA      | 2020-11-01 | "f..."  |
| 3  | GB      | 2020-09-01 | "g..."  |
| 3  | GB      | 2020-09-02 | "h..."  |
|----+---------+------------+---------|

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接