查看此问题的一种方法是使用您试图建模的实体的关系。例如,星系有星星,星星有行星,行星有月亮;它们都有一定的特征(轨道周期以天为单位,半径以公里为单位)。你可以模型与此类似:
CREATE TABLE galaxyobjects (
galaxy text,
star text,
planet text,
moon text,
spectralclass text,
radiuskm double,
orbitalperioddays double,
PRIMARY KEY ((galaxy, star), planet, moon)
);
当然,光谱型为真的只适用于star
列,但在非规范化的模型,你会看到它的每一行上。
插入一些数据之后,我的表可能看起来像这样:
[email protected]:stackoverflow> SELECT * FROM galaxyobjects;
galaxy | star | planet | moon | orbitalperioddays | radiuskm | spectralclass
-----------+------------+-------------+--------+-------------------+----------+---------------
Milky Way | Kepler-186 | Kepler-186f | n/a | 129.9459 | 7072 | M1
Milky Way | Sun | Earth | Moon | 27.3 | 3474.8 | G2
Milky Way | Sun | Earth | n/a | 365.256 | 6371 | G2
Milky Way | Sun | Jupiter | Europa | 3.551 | 1560.8 | G2
Milky Way | Sun | Jupiter | Io | 1.77 | 1821.6 | G2
Milky Way | Sun | Jupiter | n/a | 4332.59 | 71492 | G2
(6 rows)
现在,如果我想查询木星及其卫星:
[email protected]:stackoverflow> SELECT * FROM galaxyobjects
WHERE galaxy='Milky Way' AND star='Sun' and planet='Jupiter';
galaxy | star | planet | moon | orbitalperioddays | radiuskm | spectralclass
-----------+------+---------+--------+-------------------+----------+---------------
Milky Way | Sun | Jupiter | Europa | 3.551 | 1560.8 | G2
Milky Way | Sun | Jupiter | Io | 1.77 | 1821.6 | G2
Milky Way | Sun | Jupiter | n/a | 4332.59 | 71492 | G2
(3 rows)
注:
- 我指定
galaxy
和star
作为分区键。由于卡桑德拉每个分区最多有20亿列,而且一个星系绝对可以有数十亿个物体在里面进行轨道运行,所以我认为需要额外划分star
。请注意,在此模型中,您必须在每个查询中指定一个galaxy
和star
。
- 我想你可以扩展分区键以包含
planet
,但是那么你将无法查询star
的行星。
- 在此模型中,
planet
和moon
是集群密钥,因此不需要在每个查询中指定它们。但是你不能跳过它们,所以你不能指定(在你的WHERE子句中)一个moon
而不指定一个planet
。
- 我的数据建模的感觉并不真正喜欢使用
n/a
作为自己查询行星时(没有月亮)的聚类关键。所以也许有更好的方法来建模。也许一堆月亮会更合适?
为您的数据库确定正确的数据模型不仅取决于您将在数据库中拥有的内容,而且非常关注您将如何使用它 - 您的INSERT和SELECT将会如何看起来像,他们会有多少人,他们之间的比例是多少等等。 有一个关于C *数据建模的非常好的在线课程,您可能会感兴趣:https://academy.datastax.com/courses/ds220-data-modeling – uri2x