Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/cassandra/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何在cassandra中选择合适的表结构?_Cassandra_Cql_Cql3 - Fatal编程技术网

如何在cassandra中选择合适的表结构?

如何在cassandra中选择合适的表结构?,cassandra,cql,cql3,Cassandra,Cql,Cql3,假设我有一个具有以下结构的表 创建表任务( 用户id uuid, 名称文本, 任务id uuid, 说明文字, 主键((用户id)、名称、任务id) ); 它允许我按name升序获取用户的所有任务。我还在主键中添加了task\u id,以避免出现错误。以下查询适用 从任务中选择*,其中user_id=? 以及 从任务中选择*,其中user_id=?和名字>? 但是,我无法使用特定的任务id获取任务。例如,以下查询崩溃 从任务中选择*,其中user_id=?任务_id=? 由于这个

假设我有一个具有以下结构的表

创建表任务(
用户id uuid,
名称文本,
任务id uuid,
说明文字,
主键((用户id)、名称、任务id)
);

它允许我按
name
升序获取用户的所有任务。我还在主键中添加了
task\u id
,以避免出现错误。以下查询适用

从任务中选择*,其中user_id=?
以及

从任务中选择*,其中user_id=?和名字>?

但是,我无法使用特定的
任务id
获取任务。例如,以下查询崩溃

从任务中选择*,其中user_id=?任务_id=?
由于这个错误

无法限制主键列“任务id”,因为前面的列“名称”未受限制
它需要指定
name
列,但目前我只有
task\u id
(例如,来自url)和
user\u id
(来自会话)


如何创建此表以执行这两个查询?或者我需要为第二种情况创建单独的表?这种情况下的常见模式是什么?

您可以简单地添加一个与task_id值相同的冗余列taskId,并在taskId上创建一个辅助索引。 然后您可以查询
user\u id=?和tsakId=?

PRIMARY KEY column "task_id" cannot be restricted as preceding 
  column "name" is not restricted
您看到此错误是因为CQL不允许查询跳过主键组件

如何创建此表以执行这两个查询?或者我需要为第二种情况创建单独的表?这种情况下的常见模式是什么

正如您所怀疑的,使用Cassandra解决此类问题的典型方法是为每个查询创建一个附加表。在这种情况下,使用设计用于匹配附加查询模式的主键重新创建表的方式如下所示:

create table tasks_by_user_and_task (
   user_id uuid,
   name text,
   task_id uuid,
   description text,
   primary key ((user_id), task_id)
);

您只需再添加一个与task_id值相同的冗余列taskId,并在taskId上创建一个二级索引

虽然我通常不喜欢使用二级索引,但在这种情况下,它的性能可能还不错。原因是,您仍将通过分区键限制查询,这将消除检查其他节点的需要。缺点(正如Undefined_variable指出的)是无法在主键组件上创建辅助索引,因此需要复制该列(并将索引应用于非主键列)才能使该解决方案起作用


对这两种解决方案的性能进行建模和测试可能是个好主意。

如果您有额外的磁盘空间,最好的方法是在第二个表中复制数据。您应该避免在生产中使用二级索引。当然,您的应用程序需要写入这两个表。但是卡桑德拉非常擅长使这一点更有效率

create table tasks_by_name (
   user_id uuid,
   name text,
   task_id uuid,
   description text,
   primary key ((user_id), name, task_id)
);

create table tasks_by_id (
   user_id uuid,
   name text,
   task_id uuid,
   description text,
   primary key ((user_id), task_id)
);

我考虑过这个变体,实际上它是有效的。但我认为对于基数较高的列,这可能是不合适的。在本例中,我们通过用户id缩小查询范围,似乎用户的任务量并不巨大。所以索引可以起到帮助作用。但是,如果我有数十万行,我需要找到一个具体的。索引可能是低效的?