2011-09-13 2 views
1

は:Hadoop Pigでグループ化するときに、グループ化された値の文字列の衝突を検出して処理することは可能ですか?私は、ユーザー名と自分の好きな果物を示​​し、次のようなデータのラインを持っていると仮定すると

Alice\tApple 
Bob\tApple 
Charlie\tGuava 
Alice\tOrange 

私は、各ユーザの好みのフルーツを示し豚のクエリを作成したいと思います。ユーザーが複数回出現する場合、「複数」を表示したいと考えています。例えば、上記のデータと結果は次のようになります。(それは必然的に非常にうまく機能しないだろうが)SQLでは

Alice\tMultiple 
Bob\tApple 
Charlie\tGuava 

、これはこのような何かを行うことができます。

select user, case when count(fruit) > 1 then 'Multiple' else max(fruit) end 
from FruitPreferences 
group by user 

しかし、私同等のPigLatinを理解することはできません。何か案は?

+0

私はこの問題はに似ていることに注意してください、私は尋ねた、別の質問とは区別する必要がありますhttp://stackoverflow.com/questions/7406522/is-it-possible-to-cross-join-a豚の中に入れられているのとの関係で/ –

答えて

1

"Aggregate Function" Pig UDFと書いてください(「集計関数」までスクロールしてください)。これは、バッグを取り、スカラーを出力するユーザー定義の関数です。基本的に、あなたのUDFはバッグを取り込み、複数のアイテムがあるかどうかを判断し、それに応じてifステートメントで変換します。

私はUDFなしでこれを行う方法を考えることができますが、間違いなく厄介です。あなたのGROUP後、2に設定してデータを分割するSPLITを使用します。カウントはカウントが複数である1と1である1ここで:

SPLIT grouped INTO one IF COUNT(fruit) == 0, more IF COUNT(fruit) > 0; 

その後、個別に変換するために、それぞれにFOREACH ... GENERATEを使用します。最後に

one = FOREACH one GENERATE name, MAX(fruit); -- hack using MAX to get the item 
more = FOREACH more GENERATE name, 'Multiple'; 

、組合それらをバック:

out = UNION one, more; 

は、私は本当に同じダを渡すのより良い方法を発見していませんあなたが望むように、いくつかの条件に基づいて2つの異なる方法で設定されます。私はここでやったように、通常、ある種の分割/再結合をします。私はピッグがスマートで1 M/R以上の仕事を使わない計画を立てると信じています。

免責事項:現時点でこのコードを実際にテストすることはできないため、間違いがある可能性があります。


更新:

難しく見ると、私はbicond operatorを思い出すと、私はそれがここで働くだろうと思いました。

b = FOREACH a GENERATE name, (COUNT(fruit)==1 ? MAX(FRUIT) : 'Multiple'); 
+0

驚くべきことに、バイコンドオペレーターがこれに取り組むかどうかは分かりませんでした。最初。それ以外の場合は、私が説明した分割/結合方法に戻ります。 –

関連する問題