我有一个模特
class Foo {
private int id;
private String name;
private String city;
}
设置
Foo foo = new Foo();
foo.setId(1);
foo.setName("foo test");
现在我想要一个从任何对象返回非空Map的泛型方法。例如,在foo的情况下,它返回包含id
和name
的Map。任何更新?
答案 0 :(得分:1)
您可以使用com.fasterxml.jackson.databind.ObjectMapper
完成此操作。首先使用Gson
将foo对象转换为jsonString。然后将其传递给ObjectMapper
,询问Json键/值属性的映射。它会为您过滤掉空值。代码就是这样的。
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.google.gson.Gson;
public class MapTest {
public static void main(String[] args) throws JsonParseException, JsonMappingException, IOException {
Foo foo = new Foo();
foo.setId(1);
foo.setName("foo test");
final Gson gson = new Gson();
final HashMap<String, Object> result = new ObjectMapper().readValue(gson.toJson(foo),
new TypeReference<Map<String, Object>>() {
});
System.out.println(result);
}
}
答案 1 :(得分:0)
如果我清楚地理解了您的问题,您需要一种对您的输入进行操作并提供地图作为回报的方法。但是我不确定你为什么要在一个对象上做这个。我想你想要在这些对象的列表上操作。我正在为单个对象提供答案,但您也可以将解决方案扩展到支持列表或数组。
对于我的第一个解决方案,我不会使用反射,因为它不支持在非框架情况下使用正常的生产代码。
public static <K, V> Map<K, V> getGenericMap(Supplier<K> keySupplier, Supplier<V> valueSupplier) {
Map<K, V> returnMap = new HashMap<K, V>();
returnMap.put(keySupplier.get(), valueSupplier.get());
return returnMap;
}
你必须在上面打电话如下:
Foo foo = new Foo();
foo.setId(1);
foo.setName("foo test");
Map<Integer,String> map=getGenericMap(foo::getId,foo::getName);
但是,如果您真的倾向于反思解决方案,请检查下面的不推荐解决方案:
@SuppressWarnings("unchecked")
public static <K, V> Map<K, V> getGenericMap(Object obj, String keyGetterName, String valueGetterName)
throws IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException,
SecurityException {
Map<K, V> returnMap = new HashMap<K, V>();
Class<? extends Object> clazz = obj.getClass();
Method keyGetter = clazz.getDeclaredMethod(keyGetterName);
Method valueGetter = clazz.getDeclaredMethod(valueGetterName);
returnMap.put((K) keyGetter.invoke(obj), (V) valueGetter.invoke(obj));
return returnMap;
}
上面的内容必须如下所示:
Foo foo = new Foo();
foo.setId(1);
foo.setName("foo test");
Map<Integer,String> map1=getGenericMap(foo, "getId","getName");
我希望这能回答你的问题。