通常建议通过startrow
和stoprow
使用范围扫描,而不是Rowkey Prefix Filter
(例如,here)。这样做的原因是因为Rowkey Prefix Filter
导致对rowkey进行全表扫描,而通过startrow
和stoprow
进行范围扫描不会导致全表扫描。为什么不呢?大多数人都说"因为rowkey是按字典顺序存储的,"当然,这并不能解释为什么Rowkey Prefix Filter
无法利用这一点。
在任何情况下,通过startrow
和stoprow
进行范围扫描的确切方式不会导致对该rowkey进行全表扫描?
在python中使用这个小例子来说明为什么我不理解rowkeys的lexagraphical排序在避免全表扫描方面意味着什么:
rowkeys = ['a1', 'a2', 'a3', 'b1', 'b2', 'b3', 'c1', 'c2', 'c3']
def range_scan(startrow, stoprow):
is_found = False
for rowkey in rowkeys:
if startrow <= rowkey < stoprow:
is_found = True
yield rowkey
else:
if is_found:
raise StopIteration()
显然,HBase算法与此不同。怎么样?
TLDR:在使用startrow和stoprow进行范围扫描时,HBase究竟是如何避免全表扫描的?
答案 0 :(得分:6)
在HBase中,表格分为多个区域。区域是由特定区域服务器提供服务的一组行。区域服务器(通常)具有来自多个表的多个区域,用于处理请求。
因为行是按键排序的,所以在hbase master中已知哪个开始和停止键是每个区域的边界,以及可以在哪个区域服务器上查询该区域。
因此,如果完成使用显式启动和停止行的扫描,则查询仅定向到具有可能在请求范围内的键的区域/区域服务器。
如果查询具有“小”键范围,那么您会发现在几乎所有查询中只访问了一个区域。
HBase表通常有几十个区域,通过使用开始和停止行限制扫描,您可能会发现表的100个区域中的99个区域甚至不知道表上的查询完成。