복붙노트

[HADOOP] Hadoop : java.lang.ClassCastException : org.apache.hadoop.io.LongWritable을 org.apache.hadoop.io.Text로 형변환 할 수 없습니다.

HADOOP

Hadoop : java.lang.ClassCastException : org.apache.hadoop.io.LongWritable을 org.apache.hadoop.io.Text로 형변환 할 수 없습니다.

내 프로그램은 다음과 같다.

public class TopKRecord extends Configured implements Tool {

    public static class MapClass extends Mapper<Text, Text, Text, Text> {

        public void map(Text key, Text value, Context context) throws IOException, InterruptedException {
            // your map code goes here
            String[] fields = value.toString().split(",");
            String year = fields[1];
            String claims = fields[8];

            if (claims.length() > 0 && (!claims.startsWith("\""))) {
                context.write(new Text(year.toString()), new Text(claims.toString()));
            }
        }
    }
   public int run(String args[]) throws Exception {
        Job job = new Job();
        job.setJarByClass(TopKRecord.class);

        job.setMapperClass(MapClass.class);

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

        job.setJobName("TopKRecord");
        job.setMapOutputValueClass(Text.class);
        job.setNumReduceTasks(0);
        boolean success = job.waitForCompletion(true);
        return success ? 0 : 1;
    }

    public static void main(String args[]) throws Exception {
        int ret = ToolRunner.run(new TopKRecord(), args);
        System.exit(ret);
    }
}

데이터는 다음과 같습니다.

"PATENT","GYEAR","GDATE","APPYEAR","COUNTRY","POSTATE","ASSIGNEE","ASSCODE","CLAIMS","NCLASS","CAT","SUBCAT","CMADE","CRECEIVE","RATIOCIT","GENERAL","ORIGINAL","FWDAPLAG","BCKGTLAG","SELFCTUB","SELFCTLB","SECDUPBD","SECDLWBD"
3070801,1963,1096,,"BE","",,1,,269,6,69,,1,,0,,,,,,,
3070802,1963,1096,,"US","TX",,1,,2,6,63,,0,,,,,,,,,
3070803,1963,1096,,"US","IL",,1,,2,6,63,,9,,0.3704,,,,,,,
3070804,1963,1096,,"US","OH",,1,,2,6,63,,3,,0.6667,,,,,,,

이 프로그램을 실행하면 콘솔에서 다음을 볼 수 있습니다.

12/08/02 12:43:34 INFO mapred.JobClient: Task Id : attempt_201208021025_0007_m_000000_0, Status : FAILED
java.lang.ClassCastException: org.apache.hadoop.io.LongWritable cannot be cast to org.apache.hadoop.io.Text
    at com.hadoop.programs.TopKRecord$MapClass.map(TopKRecord.java:26)
    at org.apache.hadoop.mapreduce.Mapper.run(Mapper.java:144)
    at org.apache.hadoop.mapred.MapTask.runNewMapper(MapTask.java:764)
    at org.apache.hadoop.mapred.MapTask.run(MapTask.java:370)
    at org.apache.hadoop.mapred.Child$4.run(Child.java:255)
    at java.security.AccessController.doPrivileged(Native Method)
    at javax.security.auth.Subject.doAs(Subject.java:396)
    at org.apache.hadoop.security.UserGroupInformation.doAs(UserGroupInformation.java:1121)
    at org.apache.hadoop.mapred.Child.main(Child.java:249)

클래스 유형이 올바르게 매핑되었다고 생각합니다. 클래스 매퍼,

여기서 내가 잘못하고있는 것이 무엇인지 알려 주시기 바랍니다.

해결법

  1. ==============================

    1.M / R 프로그램을 사용하여 파일을 읽을 때 매퍼의 입력 키는 파일의 행 색인이어야하며 입력 값은 전체 행이어야합니다.

    M / R 프로그램을 사용하여 파일을 읽을 때 매퍼의 입력 키는 파일의 행 색인이어야하며 입력 값은 전체 행이어야합니다.

    그래서 여기서 일어나는 일은 라인 인덱스를 Text 객체로 잘못 작성하려고 시도하고 Hadoop이 타입에 대해 불평하지 않도록 대신 LongWritable이 필요하다는 것입니다.

    대신 다음을 시도하십시오.

    public class TopKRecord extends Configured implements Tool {
    
        public static class MapClass extends Mapper<LongWritable, Text, Text, Text> {
    
            public void map(LongWritable key, Text value, Context context) throws IOException, InterruptedException {
                // your map code goes here
                String[] fields = value.toString().split(",");
                String year = fields[1];
                String claims = fields[8];
    
                if (claims.length() > 0 && (!claims.startsWith("\""))) {
                    context.write(new Text(year.toString()), new Text(claims.toString()));
                }
            }
        }
    
        ...
    }
    

    또한 코드에서 재검토하고 싶은 한 가지 작업은 처리중인 모든 레코드에 대해 2 개의 Text 개체를 만드는 것입니다. 처음에는이 2 개의 객체를 생성해야하고, 매퍼에서는 set 메소드를 사용하여 값을 설정하기 만하면된다. 상당한 양의 데이터를 처리하는 경우 이렇게하면 많은 시간을 절약 할 수 있습니다.

  2. ==============================

    2.입력 형식 클래스를 설정해야합니다.

    입력 형식 클래스를 설정해야합니다.

    job.setInputFormatClass(KeyValueTextInputFormat.class);
    job.setOutputFormatClass(TextOutputFormat.class);
    
  3. from https://stackoverflow.com/questions/11784729/hadoop-java-lang-classcastexception-org-apache-hadoop-io-longwritable-cannot by cc-by-sa and MIT license