表1
create table mylistofitems (listid int,
itemid int,
quantity int,
itemdesc text,
primary key ((listid, itemid), itemdesc));
在上表中,我正在执行以下插入操作:
insert into mylistofitems (listid, itemid, itemdesc, quantity) values (1, 1000, 'apple', 5);
insert into mylistofitems (listid, itemid, itemdesc, quantity) values (1, 1000, 'banana', 10);
insert into mylistofitems (listid, itemid, itemdesc, quantity) values (1, 1000, 'orange', 6);
insert into mylistofitems (listid, itemid, itemdesc, quantity) values (1, 1000, 'orange', 50);
当我从mylistofitems中选择*时,我得到以下信息:
listid | itemid | itemdesc | quantity
--------+--------+----------+----------
1 | 1000 | apple | 5
1 | 1000 | banana | 10
1 | 1000 | orange | 50
第二个insert语句未覆盖第一行。但是第四插入语句已覆盖第三行。
在这种情况下,聚簇键是什么意思?
表2:
create table myitems (listid int,
itemid int,
idesc text,
qty int,
primary key (listid, itemid));
我将以下记录插入表2:
insert into myitems (listid, itemid, idesc, qty) values (1, 1000,
'apple', 5);
insert into myitems (listid, itemid, idesc, qty) values (1, 1000, 'banana', 10);
insert into myitems (listid, itemid, idesc, qty) values (1, 1000, 'orange', 6);
insert into myitems (listid, itemid, idesc, qty) values (1, 1000, 'orange', 50);
在表2中插入查询与表1完全相同。 但是当我从项目中选择*时,我很惊讶地看到最后插入的只有一行。其余所有行均丢失。即,每个插入语句将覆盖先前的记录。
listid | itemid | idesc | qty
--------+--------+--------+-----
1 | 1000 | orange | 50
问题: 为什么表2中的行为与表1中的行为不同? 在这种情况下,聚簇键是什么意思?为什么将集群键命名为“集群键”。它与cassandra集群有关系吗?
有关更新的问题: 我尝试对表1进行更新:
update mylistofitems set quantity = 100 where listid = 1 and itemid = 1000;
这表示错误2200,缺少某些群集密钥。为什么要限制呢?
答案 0 :(得分:0)
群集键指示数据如何在磁盘上存储。这就是Cassandra表现出色的原因之一。因为列的顺序会更改数据的存储方式,所以重要的是要知道它们是在Cassandra的内部文件中管理的。
将磁盘上的数据可视化为数组。这实际上是Cassandra将如何存储您的数据的方式。这是前三个查询后的第一个表:
table1 =
(listid(1) - itemid(1000)) // Partition key
idesc('apple') // Clustering key
= {listid: 1, itemid: 1000, idesc: apple, qty: 5}
idesc('banana') // Clustering key
= {listid: 1, itemid: 1000, idesc: banana, qty: 10}
idesc('orange') // Clustering key
= {listid: 1, itemid: 1000, idesc: orange, qty: 6}
在第四个插入中,将使用每个聚类键(在本示例中为索引)遍历数据,以查找要覆盖的最终数据。因此,在第四次插入后,它将如下所示:
table1 =
(listid(1) - itemid(1000)) // Partition key
idesc('apple') // Clustering key
= {listid: 1, itemid: 1000, idesc: apple, qty: 5}
idesc('banana') // Clustering key
= {listid: 1, itemid: 1000, idesc: banana, qty: 10}
idesc('orange') // Clustering key
= {listid: 1, itemid: 1000, idesc: orange, qty: 50}
进行以下查询,以及我像Cassandra这样的访问数据的示例。
WHERE listid IN (1, 2) and itemid = 1000
result = (data[1-1000], data[2-1000])
WHERE listid = 1 AND itemid = 1000 AND idesc = 'apple'
result = data[1-1000]['apple']
WHERE idesc = 'apple'
result = data[????]['apple']
C *不知道要搜索apple
的索引。
重要的是要注意,插入或更新数据时这是相同的。让我们以您的UPDATE
查询为例。
UPDATE mylistofitems SET quantity = 100 WHERE listid = 1 AND itemid = 1000;
使用此查询,您正在尝试执行以下操作:
`data[1-1000][????] = {listid: 1, itemid: 1000, idesc:????, qty: 1000}`
C *不知道将数据存储在哪个索引中。
您应该将查询更新为以下内容:
UPDATE mylistofitems SET quantity = 100 WHERE listid = 1 AND itemid = 1000 AND idesc = 'orange';
以数组形式看起来像:
`data[1-1000]['orange'] = {listid: 1, itemid: 1000, idesc: 'orange', qty: 1000}`
如果将quantity
添加为聚簇键,则数据结构将如下所示:
table1 =
(listid(1) - itemid(1000)) // Partition key
idesc('apple') // Clustering key
quantity(5) // Clustering key
= {listid: 1, itemid: 1000, idesc: 'apple', qty: 5}
idesc('banana') // Clustering key
quantity(10) // Clustering key
= {listid: 1, itemid: 1000, idesc: 'banana', qty: 10}
idesc('orange') // Clustering key
quantity(6) // Clustering key
= {listid: 1, itemid: 1000, idesc: 'orange', qty: 6}
quantity(50 // Clustering key
= {listid: 1, itemid: 1000, idesc: 'orange', qty: 50}
这将允许您为每个组合包含多个行,尽管您将无法具有相同数据的多个行。
答案 1 :(得分:0)
我想回答自己的问题以关闭此线程。还要帮助那些会有相同困惑的人:
基本上,我正在研究主键,分区键,集群键的概念。
表1的主键是:
primary key ((listid, itemid), itemdesc));
这意味着listid + itemid只是一个分区键,可以帮助记录找到要登陆的节点。
仅对于listid + itemid + itemdesc的组合,才会保留实际的唯一性。
总结:
listid+itemid = composite partition key
listid+itemid+itemdesc = composite primary key
itemdesc = clustering key
(集群键仅用于对每个分区下的项目进行排序,这有助于使用各种关系运算符对此列进行查询)
在这种情况下,群集只是将记录按分区键分组,并在每个分区键下的ASC(默认情况下)中对其进行排序。换句话说,它是一个分组依据和排序依据。
这与RDBMS完全不同。在RDBMS世界中,您可以根据需要在检索时使用分组和排序。在Cassandra中,我们在插入时会使用分组和排序,以便您的检索更快(取决于所使用的查询)
表2被定义为主键(listid,itemid),这意味着:
listid = standalone partition key
itemid = standalone clustering key
listid + itemid = composite primary key