2017-02-04 11 views
1

Google 구아바 라이브러리를 사용하여 언급 된 패키지에서 모든 클래스를 반복적으로 가져오고 모든 공용 메소드를 반복하고 매개 변수를 가져옵니다. "mapOfpackageMethodParameters"가 gson 객체에 전달되어 json을 제공합니다.다음 코드를 optmizing하는데 도움이 필요합니다.

lambda 또는 java8 stream api를 사용하여 두 개의 내부 루프를 최적화 할 수있는 방법이 있습니까? 다른 제안?

String[] packagenames = { "com.example" }; 
LinkedHashMap<String, LinkedHashMap<String, LinkedHashMap<String, String>>> mapOfpackageMethodParameters = new LinkedHashMap<>(); 
for (String packagename : packagenames) { 
    List<ClassInfo> clazzList = ClassPath.from(ClassLoader.getSystemClassLoader()) 
      .getTopLevelClassesRecursive(packagename).stream().filter(c -> c.getPackageName().endsWith("test")) 
      .collect(Collectors.toList()); 
    for (ClassInfo class1 : clazzList) { 
     List<Method> methodList = Arrays.asList(Class.forName(class1.getName()).getMethods()); 
     LinkedHashMap<String, LinkedHashMap<String, String>> methodMap = new LinkedHashMap<>(); 
     for (Method method : methodList) { 
      List<Parameter> parameterList = Arrays.asList(method.getParameters()); 
      LinkedHashMap<String, String> parameterMap = parameterList.stream() 
        .collect(Collectors.toMap(param -> param.getName(), param -> param.getType().toString(), 
          (x, y) -> x, LinkedHashMap::new)); 
      methodMap.put(method.getName(), parameterMap); 
     } 
     mapOfpackageMethodParameters.put(class1.getName(), methodMap); 
    } 
} 

이것은 위의 코드에서 예상되고 생성 된 최종 json입니다.

{ 
    "com.example.test.dummyclass": { 
     "sampletest1": { 
      "dummyargument1": "class java.lang.String", 
      "dummyargument2": "class java.lang.String" 
     }, 
     "sampletest2": { 
      "dummyargument1": "class java.lang.String", 
      "dummyargument2": "class java.lang.Integer" 
     } 
    } 
} 
+1

코드 복잡도의 관점에서 * 성능 * 최적화 * * 최적화를 원하십니까? – CKing

+0

대부분 복잡성을 최적화합니다. 그런데 성능은 parallelStream right를 사용하여 향상시킬 수 있습니까? –

+0

중간 방법을 작성하십시오. 한 곳에서 너무 많이 넣었 기 때문에 코드를 거의 읽을 수 없습니다. 모든 것을 gson 객체로 반환하려는 경우'PackageJson','ClassJson','MethodJson'과 같이 반환해야하는 특정 객체를 작성하는 것이 좋습니다. 그 객체들은 Gson에 의해 자동으로 변형 될 것입니다. 맵을 제거하면 전체 내용을 읽을 수 없게 만드는 제네릭이 적기 때문에 이미 복잡성을 줄이는 데 큰 도움이됩니다. –

답변

0

당신은 LinkedHashMap으로 수집하는 스트림으로 for..each 루프의 각을 변환 할 수 있습니다. 전체 작동을 매우 기능적으로 만듭니다.

String[] packageNames = { "com.example" }; 
LinkedHashMap<String, LinkedHashMap<String, LinkedHashMap<String, String>>> mapOfpackageMethodParameters = Arrays 
    .stream(packageNames) 
    .flatMap(packageName -> ClassPath 
     .from(ClassLoader.getSystemClassLoader()) 
     .getTopLevelClassesRecursive(packageName) 
     .stream()) 
    .filter(classInfo -> classInfo.getPackageName().endsWith("test")) 
    .map(ClassInfo::load) 
    .collect(Collectors.toMap(
     Class::getName, 
     clazz -> Arrays 
      .stream(clazz.getMethods()) 
      .collect(Collectors.toMap(
       Method::getName, 
       method -> Arrays 
        .stream(method.getParameters()) 
        .collect(Collectors.toMap(
         Parameter::getName, 
         param -> param.getType().toString(), 
         (x, y) -> x, LinkedHashMap::new)), 
       (x, y) -> x, LinkedHashMap::new)), 
     (x, y) -> x, LinkedHashMap::new)); 
+0

굉장하지만 "처리되지 않은 예외 유형 IOException"이 작동하지 않습니다. –

+0

@SuhailSullad 컴파일러 오류 지점의 코드 부분은 무엇입니까? 필자가 아는 한, 예외를 던지는 코드를 추가하지 않았기 때문에 문제는 원래 코드에서도 발생합니다. – 4castle

+0

원본 코드에서'IOException'이 처리되었습니다. 위의 코드를 컴파일하려고 할 때'ClassPath.from (ClassLoader.getSystemClassLoader())'라는 Eclipse 오류가 처리되지 않은 예외를 가지고 있습니다. –