我有一些包含列的数据 colA
以及 colB
,等等。对于任何行,值 colA
以及 colB
它们是不同的。
我收到这样的询问 SELECT * FROM table WHERE colA = X or colB = X
. 为了优化,我建立了索引 colA
以及 colB
在mysql中。
现在,我想在hbase中构建这个数据库,提供相同的查询。但我知道hbase没有索引,我需要设计好的行键。
我想到了这个方法:
复制mysql中的每一行。一份使用 colA + randomString
作为行键。另一方面,使用 colB + randomString
. (追加随机字符串,因为每个行键必须是唯一的)。
好:我只需要一个查询。i、 返回行键有前缀的所有行 X
坏:我把数据库的大小扩大了一倍
在保持性能的同时,还有什么替代方法更节省空间?
2条答案
按热度按时间jckbn6z71#
您可以使用columnfamily定义一个hbase表,该表的所有列都与mysql表相同。
hbase支持
SingleColumnValueFilter
filter可根据列值筛选记录。你可以把可乐和可乐的价值与OR
接线员。因此,不需要在行键中添加任何前缀或后缀。
fykwrbwg2#
你概述的方法已经足够好了。hbase是列式的,可以使用前缀压缩,它与gzip块压缩相结合将确保磁盘上的大小实际上不是有用数据大小的两倍。
事实上,即使您有一种存储一行和两个不同列的方法(并且执行您想要执行的查询),hbase仍然会在内部为每列存储两次row键。请看我在这里给出的关于hbase如何在hfile中存储数据的示例。简言之,hbase用每一个值存储整行键(尽管前缀压缩会处理此成本的摊销)。在大多数列式数据库中,您会发现类似的存储模型,这主要是因为它们是列式的,并且需要为每列存储行键。
所以,回答你的问题,你的方法很好。尽管我会将由分隔符(而不是随机字符串)分隔的原始列标识符添加到行键中,以防将来只需要为其中一列选择值。更好的是,将列标识符作为行键的前缀(而不是后缀),然后您可以传递行键筛选器(以或分隔),并且您的设置可以扩展到任意数量的列,在这些列中,您可以选择列的子集并仍然保持性能。
另一种查看它的方法是使用hbase power每秒进行数百万次写入,但在查询数据时仍保持原始的关系视图。这实际上意味着您需要对感兴趣的列使用二级索引。apachephoenix在hbase之上为您提供了所有这些;它是一个非常活跃的项目,提供了两全其美的功能(hbase的写密集型功能和类似sql的数据过滤功能),并增加了二级索引的存储成本(在任何关系数据库中都需要支付)。