2016-07-13 2 views
1

Я работаю над проектом mapreduce с использованием Hadoop. В настоящее время у меня 3 рабочих места.Использование счетчиков Hadoop - Несколько заданий

Я хочу использовать счетчики Hadoop, но проблема в том, что я хочу сделать фактическое количество в первой задаче, но получить доступ к значению счетчика в редукторе 3-го задания.

Как я могу это достичь? Где я должен определить enum? Нужно ли мне это пропускать, бросила вторую работу? Это также поможет увидеть пример кода для этого, поскольку я еще ничего не нашел.

Примечание: Я использую Hadoop 2.7.2

EDIT: Я уже пробовал подход объяснил here и это не удалось. Мое дело другое, поскольку я хочу получить доступ к счетчикам с другой работы. (не от преобразователя к редуктору).

То, что я пытался сделать: первую работу:

public static void startFirstJob(String inputPath, String outputPath) throws IOException, ClassNotFoundException, InterruptedException { 
    Configuration conf = new Configuration(); 
    Job job = Job.getInstance(conf, "wordCount"); 
    job.setJarByClass(WordCount.class); 
    job.setMapperClass(WordCountMapper.class); 
    job.setCombinerClass(WordCountReducer.class); 
    job.setReducerClass(WordCountReducer.class); 
    job.setOutputKeyClass(Text.class); 
    job.setOutputValueClass(LongWritable.class); 
    job.setInputFormatClass(SequenceFileInputFormat.class); 
    job.setOutputFormatClass(SequenceFileOutputFormat.class); 
    FileInputFormat.addInputPath(job, new Path(inputPath)); 
    FileOutputFormat.setOutputPath(job, new Path(outputPath)); 
    job.waitForCompletion(true); 
} 

Определено счетчик перечисления в другом классе:

public class CountersClass { 
    public static enum N_COUNTERS { 
     SOMECOUNT 
    } 
} 

Попытка чтения счетчика:

Cluster cluster = new Cluster(context.getConfiguration()); 
Job job = cluster.getJob(JobID.forName("wordCount")); 
Counters counters = job.getCounters(); 
CountersClass.N_COUNTERS mycounter = CountersClass.N_COUNTERS.valueOf("SOMECOUNT"); 
Counter c1 = counters.findCounter(mycounter); 
long N_Count = c1.getValue(); 
+0

Возможный дубликат [? Есть ли способ, чтобы получить доступ ряд успешных заданий карты из задачи снижения в работе MR] (http://stackoverflow.com/questions/8009802/is-there-a-way-to-access-number-of-success-map-tasks-from-a-reduce-task-in-an) – tworec

+0

Я думаю, что неплохо использовать счетчики изнутри сократить работу. см. http://stackoverflow.com/questions/8009802/is-there-a-way-to-access-number-of-successful-map-tasks-from-a-reduce-task-in-an/ – tworec

+0

Да, Я это уже видел, и я пробовал этот подход. Но в этом случае он хочет получить счетчики внутри редуктора (той же работы). Это не то же самое, что и в моем случае. –

ответ

3

Классический решение поставить значение счетчика задания, в конфигурацию последующей работы, когда вам нужно получить к нему доступ:

Поэтому убедитесь, что правильно увеличивать его в счетные работы картографа/редуктора:

context.getCounter(CountersClass.N_COUNTERS.SOMECOUNT).increment(1); 

Затем после подсчета завершения задания:

job.waitForCompletion(true); 

Counter someCount = job.getCounters().findCounter(CountersClass.N_COUNTERS.SOMECOUNT); 

//put counter value into conf object of the job where you need to access it 
//you can choose any name for the conf key really (i just used counter enum name here) 
job2.getConfiguration().setLong(CountersClass.N_COUNTERS.SOMECOUNT.name(), someCount.getValue()); 

Следующей частью является доступ к нему в другой работе в картографе/редукторе. Просто переопределяют настройки() Например:

private long someCount; 

@Override 
protected void setup(Context context) throws IOException, 
    InterruptedException { 
    super.setup(context); 
    this.someCount = context.getConfiguration().getLong(CountersClass.N_COUNTERS.SOMECOUNT.name(), 0)); 
} 
+0

Спасибо! Что делать, если в этом 'enum' есть более одного счетчика? могу ли я просто заменить 'setLong' и' getLong' на 'setEnum' и' getEnum'? Или мне нужно будет сделать это, как вы сказали, для всех счетчиков? –

+1

Каждый элемент перечисления должен соответствовать отдельному ключу конфигурации. Вы все еще используете setLong getLong для доступа к ним по соответствующим клавишам – yurgis

+0

Я знаю, что это старый вопрос. Но допустим, что задания начинаются после некоторой задержки, не будет ли замедленное задание перезаписывать счетчик, установленный ранее запущенным заданием при запуске в кластере? – user238607

2

Get счетчики в конце вашего 1-го задания и запишите их значение в файл и прочитайте его в суб-се quent job. Напишите его в HDFS, если вы хотите прочитать его из редуктора или локального файла, если вы прочитаете и инициализируете код приложения.

Counters counters = job.getCounters(); Counter c1 = counters.findCounter(COUNTER_NAME); System.out.println(c1.getDisplayName()+":"+c1.getValue());

Чтение и запись файлов является частью основных учебных пособий.

+0

Это может быть вариант. Не могли бы вы добавить часть кода, необходимую для этого? спасибо –

Смежные вопросы