我是新来的Pig,想运行两个聚合功能,但我不知道如何做到这一点。我的数据包括每行一个采购事务,其中我有一个sku(库存标识符)和客户为sku支付的价格(价格可能会有所不同):
sku price_paid
--- ----------
123 21.70
789 62.12
123 22.10
123 19.78
456 11.91
789 55.13
我想生成以下列表,其中包含sku,购买sku的次数,以及为sku支付的平均价格。列表应按计数按降序排列。
sku count ave_price_paid
--- --------- --------------
123 3 21.19
789 2 58.63
456 1 11.91
任何帮助都将不胜感激。我现在还没走远:
A = LOAD 'mydata.csv' USING PigStorage(',') AS (sku:chararray, price_paid:double);
B = GROUP A BY sku;
2条答案
按热度按时间rbpvctlc1#
聚合函数接受一包值并生成一个值。由于您要操作的包是属于groupby语句创建的关系的一部分的字段,因此我首先解释一下。
group by会将给定键具有相同值的所有记录收集到一个包中(包是无序的记录集合)。关系b的记录包含两个字段:
密钥,称为组(即sku)
一个收集的记录包,它是为它分组的别名(关系名)指定的名称(即a)。请注意下面您的包如何“继承”与a相同的模式。
让我们尝试使用descripe语句,它将向您显示关系的模式,例如,如果您这样做:
输出为:
与上述解释相对应。
考虑到这一点,现在可以执行以下语句:
count统计包中的记录数,avg平均作为输入提供的所有值,即包中元组记录的price\u paid值(注意访问它们的方式!)
然后执行排序:
完整代码如下:
有关pig内置函数的更多信息,请查看apache参考:http://pig.apache.org/docs/r0.13.0/func.html
rryofs0p2#
这对你来说应该是个窍门:
说明:
让我们从您已有的代码开始:
现在我们有了关系b,它由两个字段组成:一个组名和它对应的包。组名只是组的名称,如“123”。包将是该特定组的所有行的列表。例如:
如果你进去
DESCRIBE B;
那么你应该得到以下信息:在这个模式中,a是一个包,在一个包中可能有很多项目,每个项目都有一个sku字段和price\u paid字段。
现在我们需要使用Pig的强大
FOREACH...GENERATE
声明:上面这一行表示,对于关系b中的每一行,输出:
组的名称
这个
COUNT()
组的包数-整个包中的行数。使用AS
子句中,将此列命名为“count”,并使其成为长列。这个
AVG()
在包里所有你付出的代价中。使用AS
子句中,将此列命名为“avg”,并将其设为双精度。最后:
这将按“count”列降序排列关系c。