2012-11-14 14 views
6

2つのQualifierFiltersを使用してHBaseテーブルのスキャンをフィルタリングしたいと考えています。 特定の列 'col_A' および(!)を持つテーブルの行だけを取得することを意味します。複数のQualifierFilterをHBaseの行に適用する方法

我々の現在のアプローチは、次のようになります。両方のカラムのcol_A 'と「col_B」を持っているHBaseのテーブル内の複数の行があるが

FilterList filterList = new FilterList(FilterList.Operator.MUST_PASS_ALL); 
Filter filter1 = new QualifierFilter(CompareOp.EQUAL, new BinaryComparator("col_A".getBytes())); 
filterList.addFilter(filter1); 
Filter filter2 = new QualifierFilter(CompareOp.EQUAL, new BinaryComparator("col_B".getBytes())); 
filterList.addFilter(filter2); 

Scan scan = new Scan(); 
scan.setFilter(filterList); 
... 

ResultScannerは、このスキャンからの結果を返しません。

filter1だけをスキャンに適用すると、すべて正常に動作しますが、 'col_A'を持つすべての行が取得されます。 フィルタ2のみをスキャンに適用すると同じです。私たちは 'col_B'を持つすべての行を取得します。

これら2つのフィルタを組み合わせても、結果は得られません。

テーブルからcol_Aとcol_Bを持つ行だけを取得する正しい方法は何でしょうか?

答えて

3

次のフィルタを定義することによって、これを達成することができます

List<Filter> filters = new ArrayList<Filter>(2); 
byte[] colfam = Bytes.toBytes("c"); 
byte[] fakeValue = Bytes.toBytes("DOESNOTEXIST"); 
byte[] colA = Bytes.toBytes("col_A"); 
byte[] colB = Bytes.toBytes("col_B"); 

SingleColumnValueFilter filter1 = 
    new SingleColumnValueFilter(colfam, colA , CompareOp.NOT_EQUAL, fakeValue); 
filter1.setFilterIfMissing(true); 
filters.add(filter1); 

SingleColumnValueFilter filter2 = 
    new SingleColumnValueFilter(colfam, colB, CompareOp.NOT_EQUAL, fakeValue);   
filter2.setFilterIfMissing(true); 
filters.add(filter2); 

FilterList filterList = new FilterList(FilterList.Operator.MUST_PASS_ALL, filters); 
Scan scan = new Scan(); 
scan.setFilter(filterList); 

ここでの考え方は、あなたが探している列ごとに1 SingleColumnValueFilter、偽の値とCompareOp.NOT_EQUALオペレータとのそれぞれを定義することです。つまり、 このようなSingleColumnValueFilterは、指定された名前のすべての列を返します。

出典:http://mapredit.blogspot.com/2012/05/using-filters-in-hbase-to-match-two.html

+0

答えをありがとう。ちょうどそれを試してみて、私たちの場合にはうまくいくしかし、問題はパフォーマンスです。私は彼らがFilterListに入れられるようにフィルタが順序で評価されると仮定します。したがって、col_Aが存在する行が多数ある場合、HBaseはこの列の実際の値と照合する必要があります。それはかなり高価に聞こえる。実際のセル値がチェックされる前に、両方の列の存在を最初に評価する方法はありますか? – Henrik

+0

@Henrikあなたはどれくらいのデータを持っているのか分かりませんが、私はあなたが正しいと恐れています。別のオプションは、あなたが探している修飾子リストを取るカスタムフィルタを実装することです –

1

私は、この行が問題だと思う - あなたはそれになりたい

FilterList filterList = new FilterList(FilterList.Operator.MUST_PASS_ALL); 

-

FilterList filterList = new FilterList(FilterList.Operator.MUST_PASS_ONE); 

フィルタは両方を持つ列を見つけようとします

列修飾子とそのような列はありません

+0

ようこそ[StackOverflow](http://stackoverflow.com/about)!あなたの回答は、(a)質問が元のポスターの満足度にまだ回答されていない場合、または(b)問題に対処する別の解決策がある場合に最も高く評価されます。また、回答を構成する際に 'help'リンクを確認して、最大限の可読性を得るために回答の書式を設定する方法を学んでください。 – dg99

関連する問題