bigdecimal 平均数_MapReduce实例-必须用Combine--求平均数
本身求平均數很簡單的,必須用到combine的話我在兩個地方廢了很多時間,
一是combine的輸入不僅僅是map的輸出,還有可能是combine的輸出,所以對value的處理得分兩種情況吧;
二是結果要保留4位有效數字。。。噗,注意保留4位有效數字不等于小數點后面有四位,第二不能用parse!它只能轉成整形。
第三,代碼寫的實在比較挫,哎。
import java.io.IOException;
import java.math.BigDecimal;
import java.math.MathContext;
import java.util.StringTokenizer;
import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.io.DoubleWritable;
import org.apache.hadoop.io.LongWritable;
import org.apache.hadoop.io.Text;
import org.apache.hadoop.mapreduce.Job;
import org.apache.hadoop.mapreduce.Mapper;
import org.apache.hadoop.mapreduce.Reducer;
import org.apache.hadoop.mapreduce.lib.input.FileInputFormat;
import org.apache.hadoop.mapreduce.lib.output.FileOutputFormat;
public class Avg {
public static class Map extends
Mapper
{
protected void map(LongWritable
key, Text value, Context context)
throws
IOException, InterruptedException {
String line =
value.toString();
StringTokenizer
words = new StringTokenizer(line, "\n");
//
對每一行進行分割
while
(words.hasMoreElements()) {
StringTokenizer
tokenizerLine = new StringTokenizer(
words.nextToken());
String
strAlp = tokenizerLine.nextToken();
String
strData = tokenizerLine.nextToken();
Text
alphabet = new Text(strAlp);
Text
score = new Text(strData);
context.write(alphabet,
score);
}
}
}
public static class Combine extends
Reducer
{
//將部分和以及出現次數共同作為value
private Text tmp = new
Text();
public void reduce(Text key,
Iterable values, Context context)
throws
IOException, InterruptedException {
//
統計某字母出現次數和部分和
int sum =
0;
int count =
0;
String[]
val_input = null;
for (Text val
: values) {
if((val_input=val.toString().split(":")).length==2){
sum
+= Integer.parseInt(val_input[0].toString());
count
+=
Integer.parseInt(val_input[1].toString());?}
else{
sum
+= Integer.parseInt(val.toString());
count++;
}
}?// 設置value值為部分和以及出現次數
tmp.set(sum +
":" + count);
context.write(key, tmp);
}
}
public static class Reduce extends Reducer
{
private String tmp_sum = new
String();
private String tmp_count = new
String();
public void reduce(Text key,
Iterable values, Context context)
throws IOException, InterruptedException {
int sum_all =
0;
int count_all
=
0;?for (Text val
: values) {
String
str_tmp=val.toString();
//將部分和以及出現次數分割,分別求和
int
splitIndex = str_tmp.indexOf(":");
tmp_sum
= str_tmp.substring(0, splitIndex);
tmp_count
= str_tmp.substring(splitIndex+1);
int
int_sum = Integer.parseInt(tmp_sum);
int
int_count =
Integer.parseInt(tmp_count);?sum_all
+= int_sum;
count_all += int_count;
}?double average = (sum_all * 1.0) / (count_all *
1.0);?MathContext mathContext = new MathContext(4);
BigDecimal c = new BigDecimal(average);
BigDecimal aver_final = c.round(mathContext);
double aver_4 = aver_final.doubleValue();
String str_aver = String.valueOf(aver_4);
Text aver = new Text();
aver.set(str_aver);
context.write(key, aver);
}
}
public static void main(String[] args) throws
Exception {
Configuration conf = new
Configuration();
Job job = new Job(conf,
"Avg_use_combine");
job.setJarByClass(Avg.class);
job.setMapperClass(Map.class);
job.setCombinerClass(Combine.class);
job.setReducerClass(Reduce.class);
job.setOutputKeyClass(Text.class);
job.setOutputValueClass(Text.class);
FileInputFormat.addInputPath(job,
new Path(args[0]));
FileOutputFormat.setOutputPath(job,
new Path(args[1]));
System.exit(job.waitForCompletion(true)
? 0 : 1);
}
}
總結
以上是生活随笔為你收集整理的bigdecimal 平均数_MapReduce实例-必须用Combine--求平均数的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 生理期菠萝可以吃吗
- 下一篇: 头发白了吃什么可以变黑发