订购Cassandra的任何领域

Luk*_*101 4 sorting cql cassandra

我正在研究cassandra作为我即将到来的项目的可能解决方案.我研究的越多,我就会越多地听到在创建表时对未设置排序的字段进行排序是个坏主意.

是否有可能对任何领域进行排序?如果对不在群集中的字段进行排序会对性能产生什么影响?我需要在表格中排序或大约200万条记录.

Aar*_*ron 11

我一直听说,在创建表时,对未设置排序的字段进行排序是个坏主意.

这不是一个坏主意.实际上不可能让Cassandra按任意列对数据进行排序.Cassandra需要一种基于查询的建模方法,这也适用于排序顺序.您必须提前决定希望Cassandra支持的查询类型,以及这些查询返回其数据的顺序.

是否有可能对任何领域进行排序?

以下是Cassandra如何对结果集进行排序的事情:事实并非如此.Cassandra查询对应于分区位置,数据从磁盘读取并返回给您.如果数据的读取顺序与在磁盘上排序的顺序相同,则将对结果集进行排序.另一方面,如果您尝试多键查询或基于索引的查询,它必须跳转到不同的分区,很可能它不会以任何有意义的顺序返回.

但是,如果您提前计划,您实际上可以影响数据的磁盘排序顺序,然后在查询中利用该顺序.这可以通过称为"聚类列"的建模机制来完成.Cassandra将允许您指定多个群集列,但它们仅在单个分区中有效.

那是什么意思呢?以DataStax文档为例.

CREATE TABLE playlists (
  id uuid,
  artist text,
  album text,
  title text,
  song_order int,
  song_id uuid,
  PRIMARY KEY ((id),song_order))
WITH CLUSTERING ORDER BY (song_order ASC);
Run Code Online (Sandbox Code Playgroud)

使用此表定义,我可以playlist通过id(分区键)查询特定内容.在每个id数据中,数据将按以下顺序返回song_order:

SELECT id, song_order, album, artist, title 
FROM playlists WHERE id = 62c36092-82a1-3a00-93d1-46196ee77204
ORDER BY song_order DESC;

id                                   | song_order | album                 | artist         | title
------------------------------------------------------------------------------------------------------------------
62c36092-82a1-3a00-93d1-46196ee77204 | 4          | No One Rides For Free |      Fu Manchu |             Ojo Rojo    
62c36092-82a1-3a00-93d1-46196ee77204 | 3          |             Roll Away | Back Door Slam |  Outside Woman Blues
62c36092-82a1-3a00-93d1-46196ee77204 | 2          |          We Must Obey |      Fu Manchu |     Moving in Stereo
62c36092-82a1-3a00-93d1-46196ee77204 | 1          |          Tres Hombres |         ZZ Top |            La Grange
Run Code Online (Sandbox Code Playgroud)

在这个例子中,如果我只需要指定一个ORDER BY是否要切换排序方向.由于行以ASC结束顺序存储,我需要指定DESCDESC结束顺序查看它们.如果我按行ASC结束顺序返回行,我根本不需要指定ORDER BY.

但是,如果我想通过艺术家订购呢?还是专辑?或两者?由于一个艺术家可以有很多专辑(对于这个例子),我们将修改PRIMARY KEY定义,如下所示:

PRIMARY KEY ((id),artist,album,song_order)
Run Code Online (Sandbox Code Playgroud)

在上面运行相同的查询(减去ORDER BY)会产生以下输出:

SELECT id, song_order, album, artist, title 
FROM playlists WHERE id = 62c36092-82a1-3a00-93d1-46196ee77204;

id                                   | song_order | album                 | artist         | title
------------------------------------------------------------------------------------------------------------------
62c36092-82a1-3a00-93d1-46196ee77204 | 3          |             Roll Away | Back Door Slam |  Outside Woman Blues
62c36092-82a1-3a00-93d1-46196ee77204 | 4          | No One Rides For Free |      Fu Manchu |             Ojo Rojo    
62c36092-82a1-3a00-93d1-46196ee77204 | 2          |          We Must Obey |      Fu Manchu |     Moving in Stereo
62c36092-82a1-3a00-93d1-46196ee77204 | 1          |          Tres Hombres |         ZZ Top |            La Grange
Run Code Online (Sandbox Code Playgroud)

请注意,现在按行排序artist,然后排序album.如果我们有两首来自同一张专辑的歌曲,那么song_order接下来就是.

所以现在你可能会问"如果我只想排序album,而不是artist?" 您可以album按此排序,但不能使用此表排序.您不能跳过ORDER BY子句中的群集键.为了仅按album(而不是artist)排序,您需要设计不同的查询表.有时,Cassandra数据建模会让您复制几次数据,以便能够提供不同的查询...... 这没关系.

有关如何在利用群集顺序的同时构建数据模型的更多详细信息,请查看PlanetCassandra上的这两篇文章: