2016-04-05 47 views
0

我有用於返回對象實例的方法。使用反射獲得類實例很好。 我需要避免每次爲同一個類創建一個新對象。 我錯過了什麼?如何防止使用反射創建多個對象

private static Object getInstance(String clazz) 
{ 
    //full path of the class in the clazz 

    Class<?> c = null; 
    Object obj = null; 

    try 
    { 
     c = Class.forName(clazz); 
     System.out.println("inside ins" + c); 
     obj = c.newInstance(); 
    } 
    catch (Exception e) 
    { 
     System.out.println(e); 
    } 
    return obj; 
} 

Object inst = getInstance("com.test.Test1"); 
Method method = inst.getClass().getMethod("getVal", String.class,String.class); 
method.invoke(inst, "new params","ss"); 

感謝

+0

聽起來像你需要一個'Map '作爲緩存,基本上...... –

+0

你可以檢查instanceOf方法。 – Gopal00005

+0

...或使用IoC容器 –

回答

1

這裏是你如何才能夠着手:

private static final ConcurrentMap<String, FutureTask<Object>> INSTANCES = new ConcurrentHashMap<>(); 

private static Object getInstance(String clazz) throws InterruptedException, ExecutionException {//full path of the class in the clazz 
    FutureTask<Object> task = new FutureTask<>(() -> Class.forName(clazz).newInstance()); 
    FutureTask<Object> previous = INSTANCES.putIfAbsent(clazz, task); 
    if (previous == null) { 
     task.run(); 
    } else { 
     task = previous; 
    } 
    return task.get(); 
} 

下面是相同的代碼,但這裏的Java 1.7

private static final ConcurrentMap<String, FutureTask<Object>> INSTANCES = new ConcurrentHashMap<>(); 

private static Object getInstance(final String clazz) throws InterruptedException, ExecutionException {//full path of the class in the clazz 
    FutureTask<Object> task = new FutureTask<>(new Callable<Object>() { 
     @Override 
     public Object call() throws Exception { 
      return Class.forName(clazz).newInstance(); 
     } 
    }); 
    FutureTask<Object> previous = INSTANCES.putIfAbsent(clazz, task); 
    if (previous == null) { 
     task.run(); 
    } else { 
     task = previous; 
    } 
    return task.get(); 
} 
+0

我想你使用JRE 1.8來實現你能爲我推薦JRE 1.7嗎?我猜lambda是從1.8開始的 – Rathishkumar

+0

Java 1.7的版本增加了 –

+0

解決一個簡單的問題是一種荒謬的過於複雜的方式。 – Kayaman

0

一種可能性是實施你想返回爲單身人士的課程。然後在你的getInstance()方法中,你可以調用單例的getInstance()方法(或者你想調用它的任何東西)。因此,例如,你的單例類會是這個樣子:

public class ClassOne { 

    private static ClassOne instance; 

    public static ClassOne getInstance() { 
     if (instance==null) { 
     instance = new ClassOne(); 
     } 
     return instance; 
    } 
} 

而且你的getInstance()方法將修改這個樣子。 (請注意,該代碼尚未經過測試,但我以前正是這一點這樣做的原則絕對不工作),當一個新的實例被創建類本身的

private static Object getInstance(String clazz) {//full path of the class in the clazz 
    Class<?> c = null; 
    Object obj = null; 
    try { 
     c = Class.forName(clazz); 
     System.out.println("inside ins" + c); 
     Method method = c.getMethod("getInstance", null); 
     obj = method.invoke(null, null); 

    } catch (Exception e) { 
     System.out.println(e); 
    } 
    return obj; 
} 

所以你基本上只是委派控制。根據你想要以這種方式調用的類,可以將單例行爲抽象爲可以繼承的單獨類,但使用這種反射時可能會有點棘手。