2008-12-06 39 views
14

Tôi đang tạo trò chơi trong JAVA, nơi tôi muốn đưa ra danh sách tệp trong một thư mục nhất định trong bình của tôi để tôi có thể đảm bảo có danh sách các lớp được sử dụng trong trò chơi.Liệt kê các tệp trong thư mục của tệp JAR hiện tại

Ví dụ nói trong jar của tôi, tôi có một thư mục

mtd/entity/creep/ 

Tôi muốn có được một danh sách tất cả các file .class trong thư mục đó sử dụng mã java từ một lớp khác trong jar.

Mã tốt nhất để làm như vậy là gì?

Trả lời

8

đang java1.4 Cũ, nhưng điều đó sẽ cho bạn ý tưởng:

private static List getClassesFromJARFile(String jar, String packageName) throws Error 
{ 
    final List classes = new ArrayList(); 
    JarInputStream jarFile = null; 
    try 
    { 
     jarFile = new JarInputStream(new FileInputStream(jar)); 
     JarEntry jarEntry; 
     do 
     {  
      try 
      { 
       jarEntry = jarFile.getNextJarEntry(); 
      } 
      catch(IOException ioe) 
      { 
       throw new CCException.Error("Unable to get next jar entry from jar file '"+jar+"'", ioe); 
      } 
      if (jarEntry != null) 
      { 
       extractClassFromJar(jar, packageName, classes, jarEntry); 
      } 
     } while (jarEntry != null); 
     closeJarFile(jarFile); 
    } 
    catch(IOException ioe) 
    { 
     throw new CCException.Error("Unable to get Jar input stream from '"+jar+"'", ioe); 
    } 
    finally 
    { 
     closeJarFile(jarFile); 
    } 
    return classes; 
} 
private static void extractClassFromJar(final String jar, final String packageName, final List classes, JarEntry jarEntry) throws Error 
{ 
    String className = jarEntry.getName(); 
    if (className.endsWith(".class")) 
    { 
     className = className.substring(0, className.length() - ".class".length()); 
     if (className.startsWith(packageName)) 
     { 
      try 
      { 
       classes.add(Class.forName(className.replace('/', '.'))); 
      } catch (ClassNotFoundException cnfe) 
      { 
       throw new CCException.Error("unable to find class named " + className.replace('/', '.') + "' within jar '" + jar + "'", cnfe); 
      } 
     } 
    } 
} 
private static void closeJarFile(final JarInputStream jarFile) 
{ 
    if(jarFile != null) 
    { 
     try 
     { 
      jarFile.close(); 
     } 
     catch(IOException ioe) 
     { 
      mockAction(); 
     } 
    } 
} 
+0

Sau một chút rối tung với điều này tôi đã nó hoạt động. Cảm ơn nhiều! –

+0

Ooh, điều này xảy ra chính xác những gì tôi cần ở đây ngay bây giờ - cảm ơn !! – Dan

+0

Rất vui khi được giúp đỡ :) – VonC

-2

Đó là không thể, như Java không cung cấp truy cập trực tiếp vào jar nộp các lớp được nạp từ. Bạn có thể thử phân tích cú pháp thuộc tính hệ thống java.class.path để tìm nó, nhưng điều đó sẽ không hoạt động trong mọi hoàn cảnh. Hoặc bạn có thể hạn chế nơi tệp jar phải cư trú hoặc cung cấp danh sách các lớp theo cách khác (ví dụ: thông qua tệp kê khai).

+0

Có gì sai về câu trả lời này? Tôi giả định rằng vấn đề lớn hơn sẽ là tìm đường dẫn đến tệp jar - thực sự giải nén nội dung nên khá tầm thường. –

1

Có lẽ cách tiếp cận tốt nhất là liệt kê các lớp tại thời gian biên dịch.

Có phương pháp thời gian chạy dễ vỡ. Đưa bạn Class (MyClass.class của this.getClass()). Gọi getProtectionDomain. Gọi getCodeSource. Gọi getLocation. Gọi openConnection. (Hoặc mở tài nguyên.) Truyền tới JarURLConnection. Gọi số getJarFile. Gọi entries. Lặp lại thông qua việc kiểm tra getName. Tôi thực sự không khuyên bạn nên tiếp cận này.

+0

Ví dụ: http://stackoverflow.com/a/1429275/603516 – Vadzim

0

Hãy nhớ rằng JAR file chỉ ZIP file đổi tên, và nó rất dễ dàng để đọc nội dung của ZIP file trong Java:

File jarName = null; 
    try 
    { 
     jarName = new File (Dir.class.getProtectionDomain().getCodeSource().getLocation().toURI()); 
    } 
    catch (Exception e) 
    { 
     e.printStackTrace();  
    } 

    try 
    { 
     ZipFile zf=new ZipFile(jarName.getAbsoluteFile()); 
     Enumeration e=zf.entries(); 
     while (e.hasMoreElements()) 
     { 
      ZipEntry ze=(ZipEntry)e.nextElement(); 
      System.out.println(ze.getName()); 
     } 
     zf.close(); 
    } catch (IOException e) 
    { 
     e.printStackTrace(); 
    } 
Các vấn đề liên quan