Использование пользовательского объекта в качестве ключа, испускаемого картографом - PullRequest
1 голос
/ 12 декабря 2011

У меня есть ситуация, в которой маппер выбрасывает в качестве ключа объект пользовательского типа.Он имеет два поля: intWritable ID и массив данных IntArrayWritable.Реализация заключается в следующем.`

import java.io.*;

import org.apache.hadoop.io.*;

public class PairDocIdPerm implements WritableComparable<PairDocIdPerm> {

    public PairDocIdPerm(){
        this.permId = new IntWritable(-1);
        this.SignaturePerm = new IntArrayWritable();
    }


public IntWritable getPermId() {
        return permId;
    }



    public void setPermId(IntWritable permId) {
        this.permId = permId;
    }



    public IntArrayWritable getSignaturePerm() {
        return SignaturePerm;
    }



    public void setSignaturePerm(IntArrayWritable signaturePerm) {
        SignaturePerm = signaturePerm;
    }

    private IntWritable permId;
    private IntArrayWritable SignaturePerm;

    public PairDocIdPerm(IntWritable permId,IntArrayWritable SignaturePerm) {
   this.permId = permId;
   this.SignaturePerm = SignaturePerm;
   }



    @Override
    public void write(DataOutput out) throws IOException {
    permId.write(out);
    SignaturePerm.write(out);
    }

   @Override
    public void readFields(DataInput in) throws IOException {
    permId.readFields(in);
    SignaturePerm.readFields(in);
    }

    @Override
    public int hashCode() { // same permId must go to same reducer. there fore just permId
     return permId.get();//.hashCode(); 
    }

    @Override
    public boolean equals(Object o) {
     if (o instanceof PairDocIdPerm) {
   PairDocIdPerm tp = (PairDocIdPerm) o;
   return permId.equals(tp.permId) && SignaturePerm.equals(tp.SignaturePerm);
     }
     return false;
    }

    @Override
    public String toString() {
     return permId + "\t" +SignaturePerm.toString(); 
    }

    @Override
    public int compareTo(PairDocIdPerm tp) {
     int cmp = permId.compareTo(tp.permId);
     Writable[] ar, other;
     ar = this.SignaturePerm.get();
     other = tp.SignaturePerm.get();

    if (cmp == 0) {
     for(int i=0;i<ar.length;i++){
         if(((IntWritable)ar[i]).get() == ((IntWritable)other[i]).get()){cmp= 0;continue;}
        else if(((IntWritable)ar[i]).get() < ((IntWritable)other[i]).get()){ return -1;}
         else if(((IntWritable)ar[i]).get() > ((IntWritable)other[i]).get()){return 1;}
     }   
     }

     return cmp;
     //return 1;
   }

   }`

Мне требуется, чтобы ключи с одинаковым Id переходили к тому же редуктору с порядком их сортировки, который был закодирован в методе CompareTo.Однако, когда я использую это, мой статус выполнения работы всегда map100% уменьшить 0%.Снижение никогда не заканчивается.Что-то не так в этой реализации?В общем, что является вероятной проблемой, если состояние редуктора всегда равно 0%.

1 Ответ

1 голос
/ 12 декабря 2011

Я думаю, что это может быть возможным исключением нулевого указателя в методе чтения:

   @Override
    public void readFields(DataInput in) throws IOException {
    permId.readFields(in);
    SignaturePerm.readFields(in);
    }

В этом случае permId равен нулю. Итак, что вам нужно сделать, это:

IntWritable permId = new IntWritable();

Либо в инициализаторе поля, либо перед чтением.

Однако ваш код ужасно читать.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...