2

在工作中,我们必须为我们的客户生成一份报告,该报告在一周内多次更改其参数。此报告是从我们数据库中的单个表生成的。例如,假设一个表有 100 列,我今天必须生成一个只有 5 列的报告,但明天我必须生成其中的 95 列。考虑到这一点,我创建了一个包含指定表的所有列的 TO 类,并且我的查询返回所有列 (SELECT * FROM TABLE)。

我要创建的是一个动态表单来生成报告。我首先想到的是创建一个简单的框架,其中包含列为复选框的列列表,用户将选择他想要的列(当然有一个按钮来全选,另一个按钮取消全选)。

由于所有列的名称都与 TO 类的属性相同,因此我开发了以下代码(我有谷歌这个):

Class c = Test.class;

for(int i = 0; i < listOfAttributes.length; i++)
{
    auxText += String.valueOf( c.getMethod( "get" + listOfAttributes[i]).invoke( this, null ) );
}

这是做我需要做的更好的方法吗?

提前致谢。

观察:TO 类的 getter 具有模式“getAttribute_Name”。

注意:这个问题与用户询问如何调用某个给定名称的方法的问题不同。我知道该怎么做。我要问的是,这是否是解决我描述的问题的更好方法。

4

2 回答 2

0
Class c = Test.class;
for(int i = 0; i < listOfAttributes.length; i++)
{
    auxText += String.valueOf( c.getMethod( "get" + listOfAttributes[i]).invoke( this, null ) );
}

您可以通过 Java Bean、Introspector和更优雅地做到这一点PropertyDescriptor,但它有点冗长:

Map<String, Method> methods = new HashMap<>();
Class c = this.getClass(); // surely?
for (PropertyDescriptor pd : Introspector.getBeanInfo(c).getPropertyDescriptors())
{
    map.put(pd.getName(), pd.getReadMethod();
}
// 
for (int i = 0; i < listOfAttributes.length; i++)
{
    Method m = methods.get(listOfAttributes[i]);
    if (m == null)
        continue;
    auxText += String.valueOf(m.invoke(this, null));
}
于 2016-05-03T00:04:16.163 回答
0

我的 Java 有点受限,但我相信这与使用反射一样好。

Class<?> c = Test.class;

for (String attribute : listOfAttributes) {
    auxText += String.valueOf(c.getMethod("get" + attribute).invoke(this, null));
}

但是由于这听起来像是来自潜在的不受信任的数据,所以我建议HashMap在这种情况下使用 a ,并明确引用每种方法。首先,它明确说明了可以动态调用哪些方法。其次,它更安全,编译时错误比运行时错误要好得多。第三,它可能更快,因为它完全避免了反射。大意是这样的:

private static final HashMap<String, Supplier<Object>> methods = new HashMap<>();

// Initialize all the methods.
static {
    methods.set("Foo", Test::getFoo);
    methods.set("Bar", Test::getBar);
    // etc.
}

private String invokeGetter(String name) {
    if (methods.containsKey(name)) {
        return String.valueOf(methods.get(name).get());
    } else {
        throw new NoSuchMethodException();
    }
}

这样做听起来像是严重的 DRY 违规,但重复至少可以确保您不会意外调用不相关的 getter。

于 2016-05-02T22:50:26.197 回答