0

在这个原始数据中,我们有棒球运动员的信息,架构是:

name:chararray, team:chararray, position:bag{t:(p:chararray)}, bat:map[]

使用以下脚本,我们可以列出球员和他们打过的不同位置。我们如何计算有多少球员打过一个特定的位置?EG 有多少球员处于“指定击球手”的位置?

单个位置不能多次出现在position球员的球包中。

下面列出了示例数据的 Pig 脚本和输出。

--pig script
players = load 'baseball' as (name:chararray, team:chararray,position:bag{t:(p:chararray)}, bat:map[]);
pos     = foreach players generate name, flatten(position) as position;
groupbyposition = group pos by position;dump groupbyposition;

--dump groupbyposition (output of one position i.e Designated_hitter)
(Designated_hitter,{(Michael Young,Designated_hitter)})
4

2 回答 2

2

据我所知,你已经完成了所有的“咕噜”(哈!,猪笑话)工作。剩下要做的就是COUNTGROUP BY. 就像是:

groupbyposition = group pos by position ;
pos_count = FOREACH groupbyposition GENERATE group AS position, COUNT(pos) ;

注意:使用 UDF 可以获得更有效的解决方案。如果您关心计算某些字段,那么postion事先过滤袋子应该更有效(这就是我说 UDF 的原因,我忘了你可以只使用嵌套的FILTER)。例如:

pos = FOREACH players {
              -- you can also add the DISTINCT that alexeipab points out here
              -- make sure to change postion in the FILTER to dist!
              -- dist = DISTINCT position ;
              filt = FILTER postion BY p MATCHES 'Designated_hitter|etc.' ;
      GENERATE name, FLATTEN(filt) ;
}

如果您想要的位置都没有出现,postion那么它将创建一个空袋子。当空袋被FLATTENed 时,该行被丢弃。这意味着您将使用FLATTENN 个或更少元素的袋子(其中 N 是您想要的字段数)而不是 7-15 个(并没有真正仔细查看数据),并且GROUP数据将显着减少.

注意:我不确定这是否会明显更快(如果有的话)。此外,使用 UDF 执行嵌套FILTER可能会更快。

于 2013-09-19T12:05:34.137 回答
0

您可以使用嵌套的 DISTINCT 来获取玩家列表并对其进行计数。

players = load 'baseball' as (name:chararray, team:chararray,position:bag{t:(p:chararray)}, bat:map[]);
pos     = foreach players generate name, flatten(position) as position;
groupbyposition = group pos by position;
pos_count = foreach groupbyposition generate {
     players = DISTINCT name;
     generate group, COUNT(players) as num, pos;
}
于 2013-09-19T12:00:39.053 回答