我有两个简单的类,并使用反射模式调用invoke方法。 我想写模块编程。 假设我们在数据库中有一个保存模块名称的表:
adam
当active为true时,必须激活模块。所以当我编写程序并编译时,我不喜欢再次编译整个MyApp。所以我使用反射模式来调用模块。请看代码。
Id moduleName methodName ClassName active
1 sample a com.examle.sample true
2 SMS sendSMS com.example.SMS false
3 Email sendEmail com.example.Email false
... ... ... ...
输出
public class Sample {
public void a() {
System.out.println("Call Method a");
}
}
public class SMS {
public void sendSMS(String str) {
System.out.println("send SMS ok");
}
}
public class Email {
public void sendEmail(String str) {
System.out.println("send Email ok");
}
}
public class SampleMainClass {
public static void main(String[] args) {
//coonect to database and fetch all record in tables
while(record.next){
if (record.getActive()){
Object o = Class.forName(record.getClssName()).newInstance() ;
Method method = o.getClass().getDeclaredMethod(record.getMethodName());
method.invoke(o);
}
}
}
所以我在java 8中听到,反射模式是弃用的,而是我们可以使用消费者和供应商。
如何在java 8中使用消费者和供应商代替反射?
感谢。
答案 0 :(得分:4)
public class Q42339586 {
static class Sample {
void a() { System.out.println("a() called"); }
void b() { System.out.println("b() called"); }
}
static <T> void createInstanceAndCallMethod(
Supplier<T> instanceSupplier, Consumer<T> methodCaller) {
T o = instanceSupplier.get();
methodCaller.accept(o);
}
public static void main(String[] args) {
createInstanceAndCallMethodJava8(Sample::new, Sample::a);
}
}
在这里,createInstanceAndCallMethod
执行main()方法中的操作,但它接受参数。
Supplier
用于创建新实例,Consumer
用于调用该实例上的特定方法。在示例中,两个方法引用都作为两个参数传递。相反,您也可以使用lambda表达式并写入() -> new Sample()
和o -> o.a()
。有关详细信息,请参阅this official tutorial part。
反思的优势显而易见:
createInstanceAndCallMethod
创建一个不存在的类的实例。createInstanceAndCallMethod
调用特定类中不存在的方法。当然,只有在代码中的某个地方才能知道实际的类和方法,例如,无法从属性文件中读取类和方法名称,然后使用Java 8机制安全地创建实例并调用特定方法。
答案 1 :(得分:2)
Supplier
和function mouseover(bar)
{
d3.selectAll(".bar")
.filter(function(d){ return (d != bar);})
.transition(t)
.style("opacity", 0.5);
}
是功能接口,它们不是指反射。
这是不同的事情。
所以我在java 8中听到,反射模式是弃用的,而是我们可以使用消费者和供应商。
错误的信息。