2012-06-01 69 views
2

定義我有與Java相關的問題:讀通過可變

我想知道有沒有辦法通過一個變量(一個或多個)創建路徑類(程序)。 我正在製作一個程序,該程序將從某些網站下載圖片並將其顯示給用戶。但是,不同的網站有不同的形式,這就是爲什麼我必須定義一系列特定於每個網站的功能。它們不能放在同一個類中,因爲執行相同作業的函數(僅用於另一個站點)必須具有相同的名稱。我試圖儘可能簡單地爲其他網站添加支持。

無論如何,問題是,我可以打電話給使用一個變量來確定其位置在程序中的函數。

例如:code.picturesite.functionINeed();

code是包含所有編碼的包,並picturesite是不是一類而是含有所需類的名稱的變量 - 這樣我只能改變變量值調用不同的函數(或不同類中的相同函數)。

我真的不期望這是可能的(這是更適合你瞭解問題的性質),但有另一種方法做什麼,我想在這裏實現?

+3

你可以用反射做到這一點,儘管這樣的代碼往往是脆弱的,動詞ose,而且很難維護。 http://docs.oracle.com/javase/tutorial/reflect/index.html –

回答

2

是的,有一種方法。它被稱爲反射

給出一個包含類名稱的字符串,就可以得到這樣一個實例:如果沒有默認的構造函數

Class<?> c = Class.forName("com.foo.SomeClass"); 
Object o = c.newInstance(); // assuming there's a default constructor 

,您可以通過c.getConstructor(param1.getClass(), param2.getClass(), etc)

由於得到一個參考包含方法名稱和實例的字符串,您可以調用此方法,如下所示:

Method m = o.getClass().getMethod("someMethod", param1.getClass(), param2.getClass(), etc); 
Object result = m.invoke(o, param1, param2, etc); 
+0

非常感謝你,你已經解決了我的問題! – Karlovsky120

+0

我之前沒有足夠的聲望! ;) – Karlovsky120

2

我沒有立即看到任何內容不能由被解決,而不必包含類名稱的變量,其包含類的實例變量Stion的 - 來調用類的函數,你必須知道它實現該功能,所以你可以將該功能置於界面中。

interface SiteThatCanFoo { 
    void foo(); 
} 

而且

class SiteA extends Site implements SiteThatCanFoo { 
    public void foo() { 
     System.out.println("Foo"); 
    } 
} 

然後:

Site currentSite = getCurrentSite(); // or getSiteObjectForName(siteName), or similar 
if (SiteThatCanFoo.isAssignableFrom(currentSite.class)) { 
    ((SiteThatCanFoo)currentSite).foo(); 
} 
1

所以,你想這樣做(檢查ImageDownloader.getImageFrom法)

class SiteADownloader { 
    public static Image getImage(URI uri) { 
     System.out.println("invoking SiteADownloader on "+uri); 
     Image i = null; 
     // logic for dowlnoading image from siteA 
     return i; 
    } 
} 

class SiteBDownloader { 
    public static Image getImage(URI uri) { 
     System.out.println("invoking SiteBDownloader on "+uri); 
     Image i = null; 
     // logic for dowlnoading image from siteB 
     return i; 
    } 
} 

// MAIN CLASS 
class ImageDownloader { 
    public static Image getImageFrom(String serverName, URI uri) { 
     Image i = null; 
     try { 
      // load class 
      Class<?> c = Class.forName(serverName + "Downloader"); 
      // find method to dowload img 
      Method m = c.getDeclaredMethod("getImage", URI.class); 
      // invoke method and store result (method should be invoked on 
      // object, in case of static methods they are invoked on class 
      // object stored earlier in c reference 
      i = (Image) m.invoke(c, uri); 
     } catch (NoSuchMethodException | SecurityException 
       | IllegalAccessException | IllegalArgumentException 
       | InvocationTargetException | ClassNotFoundException e) { 
      e.printStackTrace(); 
     } 
     return i; 
    } 

    // time for test 
    public static void main(String[] args) { 
     try { 
      Image img = ImageDownloader.getImageFrom("SiteB", new URI(
        "adress")); 
     } catch (URISyntaxException e) { 
      e.printStackTrace(); 
     } 
    } 
}