2017-11-09 6 views
1

hadoop의 WordCount 프로그램에 문제가 있습니다. 단어 수는 정확하지 않지만 모든 단어에 대해 0을 표시하지만 모든 고유 단어가 출력에 표시됩니다. 나는 항아리를 실행하면Hadoop 모든 단어에 대해 0 카운트를주는 WordCount

import org.apache.hadoop.fs.Path; 
import org.apache.hadoop.mapred.*; 
import java.io.IOException; 
import java.util.*; 
import org.apache.hadoop.io.*; 


public class WordCount { 
    public static class Map 
      extends MapReduceBase 
      implements Mapper<LongWritable, Text, Text, IntWritable> { 


     private final static IntWritable one = new IntWritable(); 
     private Text word = new Text(); 

     public void map(LongWritable longWritable, Text value, 
         OutputCollector<Text, IntWritable> output, 
         Reporter reporter) throws IOException { 

      String line = value.toString(); 
      StringTokenizer tokenizer = new StringTokenizer(line); 
      while (tokenizer.hasMoreTokens()) { 
       word.set(tokenizer.nextToken()); 
       output.collect(word, one); 
      } 
     } 
    } 


    public static class Reduce 
      extends MapReduceBase 
      implements Reducer<Text, IntWritable, Text, IntWritable> { 

     public void reduce(Text key, Iterator<IntWritable> values, 
          OutputCollector<Text, IntWritable> output, 
          Reporter reporter) throws IOException { 

      int sum = 0; 
      while(values.hasNext()) { 
       sum += values.next().get(); 
      } 
      output.collect(key, new IntWritable(sum)); 
     } 
    } 

    public static void main(String[] args) throws IOException { 

     JobConf jobConf = new JobConf(WordCount.class); 
     jobConf.setJobName("wordcount"); 

     jobConf.setOutputKeyClass(Text.class); 
     jobConf.setOutputValueClass(IntWritable.class); 

     jobConf.setCombinerClass(WordCount.Reduce.class); 
     jobConf.setReducerClass(WordCount.Reduce.class); 
     jobConf.setMapperClass(WordCount.Map.class); 

     jobConf.setInputFormat(TextInputFormat.class); 
     jobConf.setOutputFormat(TextOutputFormat.class); 

     FileInputFormat.setInputPaths(jobConf, new Path(args[0])); 
     FileOutputFormat.setOutputPath(jobConf, new Path(args[1])); 

     JobClient.runJob(jobConf); 
    } 
} 

출력 파일이 생성됩니다

소스 HDFS

# filename: file01.txt 
Hello World Bye World 

# filename: file02.txt 
Hello Hadoop Bye Hadoop 

이에로드 내 샘플 데이터,이다 출력 폴더에는 다음과 같이 표시됩니다.

$ bin/hdfs dfs -cat ./output/part-00000 
17/11/09 02:50:39 WARN util.NativeCodeLoader: Unable to load native-hadoop library for your platform... using builtin-java classes where applicable 
Bye 0 
Hadoop 0 
Hello 0 
World 0 

모든 계산 수가 0이지만 구현시 오류가 발생한 부분을 찾을 수 없습니다. 난 당신의 코드 오류를 디버깅하기 위해 노력했다 그래

+0

'mapred' API는 사용되지 않습니다 코드를입니다. Hadoop 버전에 따라 패키지를 사용하십시오. 'hdfs dfs' 명령을 사용하고있는 것을 보았습니다. 새로운'mapreduce' API를 사용하길 권합니다. – philantrovert

+0

나는 그것을 시도 할 것이다. 감사. –

답변

2

은지도 클래스에 있었다

public static class Map 
     extends MapReduceBase 
     implements Mapper<LongWritable, Text, Text, IntWritable> { 


    private final static IntWritable one = new IntWritable(); 
    private Text word = new Text(); 

    public void map(LongWritable longWritable, Text value, 
        OutputCollector<Text, IntWritable> output, 
        Reporter reporter) throws IOException { 

     String line = value.toString(); 
     StringTokenizer tokenizer = new StringTokenizer(line); 
     while (tokenizer.hasMoreTokens()) { 
      word.set(tokenizer.nextToken()); 
      output.collect(word, one); 
     } 
    } 
} 

당신의 매퍼 클래스가 반환되면서 널 (null) (0) 감속기는 값을 줄일 수 없습니다 값으로, 그래서

  • 그래서 각 단어에 대한 값 1을 반환되도록 값 1을 초기화.

여기

public static class Map extends MapReduceBase implements Mapper<LongWritable, Text, Text, IntWritable> { 

    private final static IntWritable one = new IntWritable(); 
    private Text word = new Text(); 

    public void map(LongWritable longWritable, Text value, OutputCollector<Text, IntWritable> output, 
      Reporter reporter) throws IOException { 

     String line = value.toString(); 
     StringTokenizer tokenizer = new StringTokenizer(line); 
     while (tokenizer.hasMoreTokens()) { 
      word.set(tokenizer.nextToken()); 
      one.set(1); 

      output.collect(word, one); 
     } 
    } 

그것은 작동합니다 ....

+0

감사합니다. 당신의 솔루션으로, 저는 다음과 같은 계산을합니다 : '안녕 2 하둡 2 안녕 0 세상 2'. 'Hello'에 대한 카운트가 올바르지 않습니다. 나는'word.set (tokenizer.nextToken());'과'one.set (1)'행의 순서를 뒤집어서 고칠 수 있었다. Hadoop 버전 2.8.1을 사용하고 있습니다. 앞으로이 게시물의 독자들에게 답을 알려 주시기 바랍니다. –