2011-12-19 4 views
0

저는 Java를 사용하는 Windows 용 데스크톱 응용 프로그램에서 작업하고 있습니다. 내 응용 프로그램에는 .php를 모두 검색해야한다는 요구 사항이 있습니다. 이렇게하려면 재귀 메서드를 사용합니다.반복에 대한 재귀

import java.io.File; 

public class Copier { 

    public static void find(String source,String rep) { 
     File src = new File(rep); 
     if (src!= null && src.exists() && src.isDirectory()) { 
      String[] tab = src.list(); 
      if (tab != null) { 
       for(String s : tab) { 
        File srcc = new File(rep+"\\"+s); 
        if (srcc.isFile()) { 
         if (srcc.getName().matches(".*"+source+"$")) { 
          System.out.println(s); 
         } 
        } else { 
         find(source,srcc.getAbsolutePath()); 
        } 
       } 
      } else { 
       //System.out.println(" list is null"); 
      } 
     } 
    } 

    public static void main(String[] args) { 
     try { 
      find(".java", "C:\\"); 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 
    } 
} 

반복 알고리즘을 사용하여이를 수행 할 수 있습니까?

답변

1

를 볼 수 없습니다.

그러나 더 빠른 프로그램을 얻는 좋은 방법은 디렉토리의 하위를 나열 할 때 파일 필터를 사용하는 것입니다. 하나는 디렉토리 용이고 다른 하나는 일치하는 파일 용입니다 (이 파일은 java.util.regexp.Pattern을 사용해야합니다).

당신은 here를 사용하는 File.list의 과부하에 대한 문서를 찾을 수 있습니다

를 업데이트 된. 패턴의 경우 로컬 변수 (재귀를 사용하는 경우 루프 또는 데이터 멤버 외부)와 같은 것을 사용할 수 있습니다.

Pattern p = Pattern.compile(".*"+source+".*"); 
boolean found = p.matcher(p.matcher(srcc.getName()).matches()); 

아, 그런데 srcc를 파일로 변환하지 마십시오! 문자열로 작업하고 최대한 적은 수의 객체로 빌드하십시오.

+0

설명 할 수 있습니다. –

+0

고맙습니다. –

3

물론. 대기열에 breadth-first-search을 사용하십시오. C:\부터 시작하여 모든 단계에서 대기열의 최상위 폴더를 팝하고 모든 하위 폴더를 대기열의 끝에 밀어 넣습니다.

의사 코드는 다음과 같습니다 당신이 이론적으로 무엇을 당신이 찾고있는 것은 가능하지만 재귀 없애 싶어 왜

queue.push("C:\"); 
while (!queue.empty()) { 
    String topFolder = queue.pop(); 
    foreach (subFolder of topFolder) { 
     queue.push(subFolder); 
    } 
} 
+0

스택을 사용해 주셔서 감사합니다. –

+0

@Anouar Elmekki - 왜 스택? 대기열이 여기에 완벽합니다. 그런데 모든 재귀 함수는 스택을 사용하여 반복적 인 함수로 바뀔 수 있지만 너무 복잡합니다. –

+0

자바로이 코드를 작성해 주시겠습니까? –

1

재귀 대신 항상 대기열을 사용할 수 있습니다. 이 경우에는 코드를 좀 더보기 쉽게 보입니다. 종종 반복적 인 구현보다는 반복적 인 구현보다 나은 성능을 얻을 수 있지만,이 경우 둘 다 거의 동일한 속도로 실행됩니다 (최소한 내 컴퓨터에서는).

public static List<String> find(final String source, final String directory) 
{ 
    List<String> results = new LinkedList<String>(); 
    Stack<String> stack = new Stack<String>(); 

    stack.add(directory); 

    String rep; 
    while (!stack.isEmpty()) { 
     rep = stack.pop(); 
     File src = new File(rep); 
     if (src != null && src.exists() && src.isDirectory()) { 
      String[] tab = src.list(); 
      if (tab != null) { 
       for (String s : tab) { 
        File srcc = new File(rep + File.separatorChar + s); 
        if (srcc.isFile()) { 
         if (srcc.getName().matches(".*" + source + "$")) { 
          // System.out.println(s); 
          results.add(s); 
         } 
        } else { 
         stack.add(srcc.getAbsolutePath()); 
        } 
       } 
      } else { 
       // System.out.println(" list is null"); 
      } 
     } 
    } 
    return results; 
} 
+0

@Petar Minchev 대기열보다 스택이 더 빠르게 (~ 15 %) 실행됩니다 (적어도 연결된 목록 구현 중 열). –

+0

고맙습니다. 내 친구 –

관련 문제