2017-11-07 10 views
0

Java에서 각 요소의 유형과 색인을 가져 오는 방법을 찾고 있습니다. 예를 들어, 그럼 난RDD는 각 요소의 유형과 색인을 가져옵니다.

[(0, int),(1, int),(2, String),(3, Double),(0, int) ........] 

그래서 키로 줄이고 각 열에 대한 데이터 유형을 볼 수 싶은 RDD

['0,1,hi,1.0', '2,3,String,String2', '1.0,2.0,3,String'] 

가 가정합니다. 나는 파이썬으로 그것을 달성했지만, 자바에서 이것을하는 방법에 대해서는 확신하지 못했다. 이 일을 할 수있는 방법이 있습니까? 다음은 내가 파이썬으로 어떻게 그랬는가이다.

def infer_type(partition): 
for row in partition: 
    value = "" 
    idx = 0 
    for i in range(len(row)): 
     if row[0] == self.prop.comment: 
      break 
     if row[i] == self.prop.delimiter or i == (len(row) - 1): 
      if i == len(row) - 1: 
       value += str(row[i]) 
      if bool(value.strip()) == False: 
       yield (idx, 'None') 
      elif int_regex_match.match(value): 
       yield (idx, 'int') 
      elif float_regex_match.match(value): 
       yield (idx, 'float') 
      else: 
       if date_regex_match.match(value): 
        yield (idx, 'date') 
       else: 
        yield (idx, 'str') 
       idx += 1 
       value = "" 
     else: 
      value += str(row[i]) 
    rdd = rdd.mapPartitions(infer_type).map(lambda x: ((x[0], x[1]), 1)).reduceByKey(add).map(
    lambda x: (x[0][0], (x[0][1], x[1]))) 

EDIT : 이것은 내가 지금까지 가지고있는 것이다. 그러나, 튜플 반복자를 얻을 수 없습니다.

PairFlatMapFunction map = new PairFlatMapFunction<Iterator<String>, Integer, String>(){ 

     @Override 
     public Iterator<Tuple2<Integer, String>> call(Iterator<String> iterator) throws Exception { 
      // TODO Auto-generated method stub 
      while(iterator.hasNext()) { 
       String[] row = iterator.next().split(","); 
       for(int j = 0; j<row.length;j++) { 
        if(row[j].matches(int_regex)) { 
         Tuple2<Integer, String> result =new Tuple2(j, "int"); 
         // return iterator of result..? 
        }else if(row[j].matches(float_regex)) { 
         Tuple2<Integer, String> result =new Tuple2(j, "float"); 
         // return iterator of result..? 
        }else if(row[j].matches(date_regex_match)) { 
         Tuple2<Integer, String> result =new Tuple2(j, "date"); 
         // return iterator of result..? 
        }else { 
         Tuple2<Integer, String> result =new Tuple2(j, "str"); 
         // return iterator of result..? 
        } 
       } 
      } 
     } 
}; 
JavaPairRDD pair_rdd = rdd.mapPartitionsToPair(map, false); 

답변

0

당신이 표현한 바에 따르면, 나는 단순히 맵 대신 mapPartition을 사용하는 이유를 알 수 없습니다. 또 다른 실수는 mapToPair 대신 flatMapToPair를 사용해야한다는 것입니다.

원하는 것을 얻으려면 flatmap 함수가 문자열 (예 : "0,1, hi, 1.0")을 튜플의 반복자에 매핑해야합니다. 당신이 실제로 mapPartition를 사용해야 할 경우

@Override 
public Iterator<Tuple2<Integer, String>> call(String row) throws Exception { 
    String[] split_row = row.split(","); 
    //create list 
    List<Tuple2<Integer, String>> result = new ArrayList<>() 
    for(int j = 0; j<split_row.length;j++) { 
     if(split_row[j].matches(int_regex)) { 
      result.add(new Tuple2(j, "int")); 
     } //else ... 
    } 
    //return the iterator 
    return result.iterator(); 
} 

, 당신은 당신의 기능에 동일한 논리를 적용 할 수 있습니다 그렇게하려면, 당신은 단순히 당신이 계산 결과의 ArrayList를 만들 수 있습니다.

+0

mapPartition을 읽은 후 성능이 향상되었으므로 mapPartition을 사용하고 싶습니다. 그렇지 않니? –

+0

String [] row = iterator.next(). split (","); -> iterator는 어디서 오는가? –

+0

질문에서 코드를 붙여 넣고 해당 부분을 수정하는 것을 잊어 버렸습니다. 나는 내 대답을 편집했다. 고마워 ;-) – Oli