如何在Pig Latin中按disctrict和year分组计算HOMICIDES占比?
用Pig Latin计算各District、Year中HOMICIDES的占比
没问题!我来一步步带你实现这个需求,咱们分步骤写Pig脚本就行:
1. 加载原始数据表
首先得把数据加载进来,假设你的数据是CSV格式(如果是其他分隔符,把','换成对应符号即可),先定义好表的字段结构:
-- 加载数据,指定列名与对应数据类型 raw_data = LOAD '/path/to/your/data' USING PigStorage(',') AS (typeofcrime:chararray, district:chararray, year:int);
2. 计算每个District+Year的总案件数
要算占比,首先得拿到每个区域每年的总案件量:
-- 按district和year组合分组,统计每组的总案件数 total_cases = FOREACH (GROUP raw_data BY (district, year)) GENERATE FLATTEN(group) AS (district, year), COUNT(raw_data) AS total_count;
3. 筛选并统计每个District+Year的HOMICIDES案件数
接下来单独提取凶杀案记录,同样按区域和年份分组统计数量:
-- 过滤出typeofcrime为HOMICIDES的记录(如果大小写不统一,可改用UPPER(typeofcrime) == 'HOMICIDES') homicide_data = FILTER raw_data BY typeofcrime == 'HOMICIDES'; -- 分组统计凶杀案数量 homicide_cases = FOREACH (GROUP homicide_data BY (district, year)) GENERATE FLATTEN(group) AS (district, year), COUNT(homicide_data) AS homicide_count;
4. 关联数据并计算占比
现在把总案件数和凶杀案数关联起来,计算占比(这里转成百分比格式,保留两位小数):
-- 按district+year左连接两个数据集,确保没有凶杀案的区域也能显示占比0 joined_data = JOIN total_cases BY (district, year) LEFT OUTER, homicide_cases BY (district, year); -- 计算占比,处理homicide_count为空的情况(设为0),同时避免整数除法问题 homicide_ratio = FOREACH joined_data GENERATE total_cases::district AS district, total_cases::year AS year, (CASE WHEN homicide_cases::homicide_count IS NULL THEN 0 ELSE homicide_cases::homicide_count END) AS homicide_count, total_cases::total_count AS total_count, ROUND((CASE WHEN total_cases::total_count == 0 THEN 0 WHEN homicide_cases::homicide_count IS NULL THEN 0 ELSE (homicide_cases::homicide_count / (double)total_cases::total_count) * 100 END), 2) AS homicide_percentage;
5. 输出结果
最后把计算好的结果保存到指定路径:
-- 存储结果,用逗号分隔字段 STORE homicide_ratio INTO '/path/to/output' USING PigStorage(',');
额外提示
- 如果数据里存在
typeofcrime大小写混乱的情况,记得用UPPER()或LOWER()统一格式后再过滤。 - 加了总案件数为0的判断,避免出现除以0的报错。
- 做除法时把整数转成
double类型,防止只得到整数结果(比如1/2会变成0.5而不是0)。
内容的提问来源于stack exchange,提问作者Kenzo Guibeb
相关产品推荐
相关产品推荐

