`
cloudeagle_bupt
  • 浏览: 541160 次
文章分类
社区版块
存档分类
最新评论

反射机制进行动态调用的两种创建方法实例与hama中的反射机制

 
阅读更多
package combine.invokeTest;
public class InvokeTest {

	public static BaseClass getClass(String className) throws ClassNotFoundException {
		return (BaseClass) ClassFactory.newInstance1(className);
//		return (BaseClass) ClassFactory.newInstance2(className);
	}
	
	public static void main(String[] args) throws InstantiationException,
			IllegalAccessException, SecurityException {
		try {
			String className = "combine.invokeTest.SubClass" ;
			BaseClass bClass = getClass(className) ;
			bClass.f() ;
		} catch (ClassNotFoundException e) {
			e.printStackTrace();
		} catch (IllegalArgumentException e) {
			e.printStackTrace();
		} 
	}
}


class BaseClass {

	BaseClass() {
		System.out.println("BaseClass Construct!");
	}

	public void f() {
		System.out.println("BaseClass! ");
	}
}

class SubClass extends BaseClass {
	SubClass() {
		System.out.println("SubClass Construct!");
	}

	public void f() {
		System.out.println("SubClass!");
	}
}


package combine.invokeTest;

import java.lang.reflect.Constructor;

import org.apache.hadoop.conf.Configuration;

public class ClassFactory {
	private static final Class<?>[] EMPTY_ARRAY = new Class[]{};
	
	public static <T> T newInstance1(String classPath) {
		T result;
		try {
			Class<?> policy = Class.forName(classPath);  
			result = (T) policy.newInstance();  //采用Class对象的newInstance
		} catch (Exception e) {
			throw new RuntimeException(e);
		}
		return result;
	}

	public static <T> T newInstance2( String classPath) {
		T result;
		try {
			Class<?>  theClass = Class.forName(classPath);
			Constructor<T> meth = (Constructor<T>)theClass.getDeclaredConstructor(EMPTY_ARRAY);
			meth.setAccessible(true);
			result = meth.newInstance();       //采用Constructor对象的newInstance
		} catch (Exception e) {
			throw new RuntimeException(e);
		}
		return result;
	}
}


上述代码中,String className也可以作为Conf从配置文件中读取,参考Hama中的反射工厂实现代码;

public class MessageManagerFactory {
  public static final String MESSAGE_MANAGER_CLASS = "hama.messenger.class";

  /**
   * Returns a messenger via reflection based on what was configured.
   * 
   * @param conf
   * @return a messenger that was configured.
   */
  @SuppressWarnings("unchecked")
  public static <M extends Writable> MessageManager<M> getMessageManager(
      Configuration conf) throws ClassNotFoundException {
    return (MessageManager<M>) ReflectionUtils.newInstance(conf
        .getClassByName(conf.get(MESSAGE_MANAGER_CLASS,
            org.apache.hama.bsp.message.HamaMessageManagerImpl.class
                .getCanonicalName())), conf);
  }

}


进入ReflectionUtils类,

  public static <T> T newInstance(Class<T> theClass, Configuration conf) {
    T result;
    try {
      Constructor<T> meth = (Constructor<T>) CONSTRUCTOR_CACHE.get(theClass);
      if (meth == null) {
        meth = theClass.getDeclaredConstructor(EMPTY_ARRAY);
        meth.setAccessible(true);
        CONSTRUCTOR_CACHE.put(theClass, meth);
      }
      result = meth.newInstance(); //使用java.lang.reflect.Constructor<T>创建的constructor创建实例
    } catch (Exception e) {
      throw new RuntimeException(e);
    }
    setConf(result, conf);
    return result;
  }



分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics