我有一个程序可以进行一些相当密集的计算,我想在Cassandra表中缓存这些计算的结果。用于执行此操作的最佳架构是什么?
目前,我正在使用以下架构:
CREATE TABLE raw_data_cache (
id uuid,
buckets int,
start_time timestamp,
end_time timestamp,
time timestamp,
data list<float>,
PRIMARY KEY(id,buckets,start_time,end_time,time)
) with GC_Grace_Seconds=1;
id
是数据源的ID,buckets
,start_time
和end_time
是处理参数。 Time
是每列唯一的“键”。 data
是时间序列数据值。
要将数据插入表中,我使用标准插入和超时:
INSERT INTO raw_data_cache (id,buckets,start_time,end_time,time,data) VALUES
(?,?,?,?,?,?) USING TTL 360;
这个架构的问题是我最终获得了一致的读取超时,我认为这是由于墓碑的数量:Read 0 live and 3777400 tombstoned cells
(取自cqlsh中的“tracing on”)。
我可以使用nodetool
摆脱所有这些,但我不想每隔几分钟就这样做。是否有更好的架构或用法可以改善这种情况?
修改:
raw_data_cache
是用于存储raw_data
的已处理版本的表。除了raw_data
之外,我一直遵循传统智慧来存储list<floats>
(但那是因为我每次都有几个不同的输入,我希望一次性获得所有这些输入)。这是基准时间序列:
CREATE TABLE raw_data(
id uuid,
time timestamp,
data list<float>,
PRIMARY KEY (id, time)
);
我与raw_data_cache
的目标是将原始数据的较小处理版本保存几个小时。
答案 0 :(得分:2)
我认为您的数据模型并未真正针对此用途进行优化。我认为你应该使用更多基于时间序列的方法。包含要缓存的每个时间段的列。我不是100%肯定,但认为GC_Grace_Seconds = 1可能不是你真正想要的。
这是Cassandra数据建模的最佳资源之一:http://planetcassandra.org/blog/post/getting-started-with-time-series-data-modeling。此外,同一作者还有3个关于该主题的视频。
如果您想优化获取最新项目,可以执行以下操作:
CREATE TABLE raw_data(
id uuid,
time timestamp,
data list<float>,
PRIMARY KEY (id, time)
) WITH CLUSTERING ORDER BY (event_time DESC);
哪个会使最新的事件成为第一个,这在缓存中很有帮助。如果你想要基于小时数的桶。您可以执行之前在包含小时'2013-10-27 12'的日期示例中执行的相同操作,并且它会将所有小时数归于该存储桶中。所以也许你可以尝试类似的东西:
CREATE TABLE summarized_data_cache(
id uuid,
time_bucket text,
time timestamp,
data list<float>,
PRIMARY KEY ((id, time_bucket), time)
);
写入速度快,但检索速度快,因为所有内容都存储在一行中。