복붙노트

[HADOOP] 평균을 찾기 위해지도 / 직무 작업 작성에 도움이 필요합니다

HADOOP

평균을 찾기 위해지도 / 직무 작업 작성에 도움이 필요합니다

저는 하둡 맵 / 리 듀스를 처음 접했습니다. 아래와 같이 입력 텍스트 파일이 주어지면 n 프로세스가 걸리는 평균 시간을 찾기 위해 Map / Reduce 작업을 작성하려고합니다.

ProcessName Time
process1    10
process2    20
processn    30

몇 가지 자습서를 겪었지만 여전히 철저한 이해가 불가능합니다. 이 문제에 대해 매퍼 및 리듀서 클래스는 어떻게해야합니까? 내 출력이 항상 텍스트 파일입니까 아니면 평균을 일종의 변수에 직접 저장할 수 있습니까?

감사.

해결법

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

    1.매퍼는 텍스트 파일을 읽고 모든 줄에 다음과 같은 맵 기능을 적용합니다

    매퍼는 텍스트 파일을 읽고 모든 줄에 다음과 같은 맵 기능을 적용합니다

    map: (key, value)
      time = value[2]
      emit("1", time)
    

    모든 맵 호출은 하나의 단일 감소 기능으로 처리되는 키 "1"을 방출합니다.

    reduce: (key, values)
      result = sum(values) / n
      emit("1", result)
    

    Hadoop을 사용하고 있기 때문에 map 함수에서 StringTokenizer를 사용하는 것을 보았을 것입니다.이 기능을 사용하면 한 줄로 시간 만 얻을 수 있습니다. 또한 n (프로세스 수)을 계산하는 방법을 생각할 수 있습니다. 예를 들어 줄을 계산하는 다른 작업의 카운터를 사용할 수 있습니다.

    최신 정보 이 작업을 실행하려면 각 회선마다 튜플을 감속기로 보내야하므로 여러 시스템에서 Hadoop 클러스터를 실행하면 네트워크가 막힐 수 있습니다. 보다 영리한 접근 방식은 입력에 더 가까운 시간의 합계를 계산할 수 있습니다. 결합기를 지정하여 :

    combine: (key, values)
      emit(key, sum(values))
    

    그런 다음이 컴 바이 너는 동일한 시스템의 모든 맵 기능의 결과 (즉, 네트워크 간 네트워킹없이)에서 실행됩니다. 그러면 리듀서는 로그 파일의 행 수가 아니라 클러스터에 기계가있는 수만큼의 튜플을 가져옵니다.

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

    2.매퍼는 입력을 평균을 구하려는 값으로 매핑합니다. 입력 내용이 다음과 같은 형식의 텍스트 파일이라고 가정 해 봅시다.

    매퍼는 입력을 평균을 구하려는 값으로 매핑합니다. 입력 내용이 다음과 같은 형식의 텍스트 파일이라고 가정 해 봅시다.

    ProcessName Time
    process1    10
    process2    20
    .
    .
    .
    

    그런 다음 파일의 각 줄을 가져 와서 나누고 두 번째 열을 잡고 해당 열의 값을 IntWritable (또는 다른 쓰기 가능한 숫자 형식)로 출력해야합니다. 프로세스 이름 또는 다른 항목으로 그룹화되지 않은 모든 시간의 평균을 원하므로 단일 고정 키가 있습니다. 따라서 매퍼는 다음과 같이 보입니다.

    private IntWritable one = new IntWritable(1);
    private IntWritable output = new IntWritable();
    proctected void map(LongWritable key, Text value, Context context) {
        String[] fields = value.split("\t");
        output.set(Integer.parseInt(fields[1]));
        context.write(one, output);
    }
    

    감속기는 이러한 값을 가져 와서 평균을 간단히 계산합니다. 이것은 다음과 같이 보일 것입니다

    IntWritable one = new IntWritable(1);
    DoubleWritable average = new DoubleWritable();
    protected void reduce(IntWritable key, Iterable<IntWrtiable> values, Context context) {
        int sum = 0;
        int count = 0;
        for(IntWritable value : values) {
            sum += value.get();
            count++;
        }
        average.set(sum / (double) count);
        context.Write(key, average);
    }
    

    여기에서는 입력 형식과 그렇지 않은 것에 대해 많은 가정을하고 있지만 합리적인 가정이므로 정확한 요구에 맞게 조정할 수 있어야합니다.

    여기 몇 가지 옵션이 있습니다. 예를 들어 작업의 출력을 후 처리 (단일 파일로 작성)하거나 단일 값을 계산하므로 결과를 카운터에 저장할 수 있습니다.

  3. from https://stackoverflow.com/questions/18062476/need-help-in-writing-map-reduce-job-to-find-average by cc-by-sa and MIT license