我有虚拟组织的ArrayList。 这些对象有很多属性和相应的get / set方法。 我想排序在此基础上,我会在运行时得到一个属性这个数组列表。 让我详细解释。 我的VO是这样的
public class Employee {
String name;
String id;
private String getName() {
return name;
}
private String getId() {
return id;
}
}
我会得到在运行时字符串“sortType”,它可以是“身份证”或“名”。 我要排序基于字符串的值列表。
我曾尝试使用比较和反思起来,但没有运气。 可能是我没有使用它properly.I不希望的,如果循环使用,创造新的比较类。 没有其他的想法?
在尝试捕捉应该是新类里。 这里是工作的代码。 如果你想使用一个单独的类的比较,请找到它@下面波西米亚的评论。
String sortType = "name"; // determined at runtime
Collections.sort(results, new Comparator<Employee>() {
public int compare(Employee c1, Employee c2) {
try{
Method m = c1.getClass().getMethod("get" + StringUtils.capitalize(sortType));
String s1 = (String)m.invoke(c1);
String s2 = (String)m.invoke(c2);
return s1.compareTo(s2);
}
catch (Exception e) {
return 0;
}
}
});
创建Comparator
作业:
public class EmployeeComparator implements Comparator<Employee> {
private final String type;
public EmployeeComparator (String type) {
this.type = type;
}
public int compare(Employee e1, Employee e2) {
if (type.equals("name")) {
return e1.getName().compareTo(e2.getName());
}
return e1.getId().compareTo(e2.getId());
}
}
然后用它
String type = "name"; // determined at runtime
Collections.sort(list, new EmployeeComparator(type));
反射版本是相似的,但你能看到的“得到” +类型(大写)的对象上的方法,并调用该和它硬铸铁可比和使用的compareTo(我会尽量表现出的代码,但我“M用我的iPhone和它的一个有点夸张,但在这里不用)
public class DynamicComparator implements Comparator<Object> {
private final String type;
// pass in type capitalised, eg "Name"
// ie the getter method name minus the "get"
public DynamicComparator (String type) {
this.type = type;
}
public int compare(Object o1, Object o2) {
// try-catch omitted
Method m = o1.getClass().getMethod("get" + type);
String s1 = (String)m.invoke(o1);
String s2 = (String)m.invoke(o2);
return s1.compareTo(s2);
}
}
OK ...以下是如何做到这一点,而无需创建一个类,使用匿名类(例外处理的代码编译):
List<?> list;
final String attribute = "Name"; // for example. Also, this is case-sensitive
Collections.sort(list, new Comparator<Object>() {
public int compare(Object o1, Object o2) {
try {
Method m = o1.getClass().getMethod("get" + attribute);
// Assume String type. If different, you must handle each type
String s1 = (String) m.invoke(o1);
String s2 = (String) m.invoke(o2);
return s1.compareTo(s2);
// simply re-throw checked exceptions wrapped in an unchecked exception
} catch (SecurityException e) {
throw new RuntimeException(e);
} catch (NoSuchMethodException e) {
throw new RuntimeException(e);
} catch (IllegalAccessException e) {
throw new RuntimeException(e);
} catch (InvocationTargetException e) {
throw new RuntimeException(e);
}
}
});
把事情简单化!
如果选择的是唯一的id
或name
-使用if语句。
两种选择之间采摘。 这是否已经发明了什么。
或者,如果它是许多属性,然后使用反射,或存储数据的Map
摆在首位。 有时候Map
是不是一个好班。 特别是如果你的VO必须不低于getter和setter等方法。
注意,虽然使用反射可能会在这种情况下不安全的客户端可能会在攻击类似于SQL注入注入的CGI参数的任何条款。