我想在cassandra中存储类似数组的对象,但是我也需要使用cql访问每个元素,因此我需要构建索引。不幸的是,数组的大小是动态的(但不是预定义的维数)。什么是最合适的存储数组的方式,如:

matrix[x][y][z]

因此,如果它将是一维(vector[n])数组,则将非常简单。我猜超级列会是合适的,例如

{key=1000 ,
    { 'matrix[]' : {
            key=0, {value:10),
            key=1, {value:33),
            ...
            key=n, {value:x)
        }
    }
}`


多维数组(matrix[x][y][z])有点复杂,我将它们存储为:

{key=1000,
    { 'matrix[ ][ ][ ]' :
        {
            key=0, {x=0, y=0, z=0, value:10),
            key=1, {x=0, y=0, z=1, value:33),
            ...
            key=whatever, {x=m, y=n, z=o, value:10),
        }
    }
}


但是在两种情况下,我都无法弄清楚如何定义column_validation_classes(我正在使用pycassa)...

我还尝试使用复合比较器,并将所有内容放在标准列中,例如:

对于一个维度:

{key=1000,
    {
        ('matrix[ ]', 0) : 10,
        ('matrix[ ]', 1) : 33,
        ...
        ('matrix[ ]', n) : x
    }
}


或多个维度:

{key=1000,
    {
        ('matrix[ ][ ][ ]', 0,0,0) : 10,
        ('matrix[ ][ ][ ]', 0,0,1) : 33,
        ...
        ('matrix[ ][ ][ ]', m,n,o) : 10
    }
}


但是对于这种情况,如果我想添加其他列以及其他信息,我将不知道如何正确定义比较器:

{key=1000,
    {
        ('matrix[ ][ ][ ]', 0,0,0) : 10,
        ...
        ('matrix[ ][ ][ ]', m,n,o) : 10,
        'whatever' : 'who cares ...',
        ...
    }
}


此外,我无法弄清楚如何为此建立索引以及如何为复合比较器创建选择语句。

感谢您对我的问题的任何建议,想法或解决方案;)

干杯

最佳答案

在Cassandra中,如何存储数据(选择行键和列名)取决于您以后要访问它的方式。

如果所有坐标都是整数,那么我建议您使用
CompositeType(LongType,LongType,LongType)作为列名。

这样一来,您就可以通过某些坐标进行搜索,方法是,将同一列写入以下关键字,以对数据进行非规范化处理(所有维度的示例)


DynamicCompositeType(x:LongType)
DynamicCompositeType(y:LongType)
DynamicCompositeType(z:LongType)
DynamicCompositeType(x:LongType,y:LongType)
DynamicCompositeType(x:LongType,z:LongType)
DynamicCompositeType(y:LongType,z:LongType)


最终以

第[x]行
=>列[x,y,z]:{“ stuff”:“真的吗?” ...}
第[y]行
=>列[x,y,z]:{“ stuff”:“真的吗?” ...}
第[z]行
=>列[x,y,z]:{“ stuff”:“真的吗?” ...}
[x,y]行
=>列[x,y,z]:{“ stuff”:“真的吗?” ...}
[x,z]行
=>列[x,y,z]:{“ stuff”:“真的吗?” ...}
[y,z]行
=>列[x,y,z]:{“ stuff”:“真的吗?” ...}

(所有键都是[x,y,z]的幂集的元素)

如果您认为将始终知道一个点的所有三个坐标,则可以围绕所有维度进行存储分区以获取行键。
假设您要为3D矩阵使用64 * 64 * 64的存储桶,则可以将点[x,y,z]保存如下:

其中X =(int)(x / 64),Z =(int)(z / 64)和Y =(int)(y / 64)

第[X,Y,Z]行
=>列[x,y,z]:{“ stuff”:“真的吗?” ...}

作为复合的替代方法,串联字符串可以正常工作。如果这样做,别忘了写前导零,否则,如果您要依靠比较器对列进行排序,那么列的顺序可能会给您带来麻烦。

关于数据存储的注意事项

至于存储数据,我建议将小的POJO序列化放入一列中,如果您希望能够使用范围查询恢复一组元素,则不要每行保存一个元素。
我最喜欢在Cassandra列中使用的序列化方法是Jackson Json字节或protobuf,如果您不愿意用它定义所有对象。
远离超级专栏...远离!或使用复合列或动态组合列(如果不是所有的列都包含相同的格式和数量的字段)

09-28 08:44