动态properties转换

今天同事和我讨论他遇到的一个问题。具体要求是这样的,在运行时,我们会从模块G得到一个Map,这个Map里面都是一些字符串对,你可以理解成一个字典,有字符串的key和字符串的value。简短节说,就是
[code]Map<String, String>[/code]
非常非常复杂深奥。

好,现在我们事先知道要从这个map里读取一些数据点,比如:id, name, sex等等。

对id,我们知道读出来的是int;对name,是string;对sex,应该对应一个叫Gender的enum类型。

这就涉及一个自动类型转换的问题。我们希望不用对每个数据点做手工类型转换。

另外一个需求,一些数据点是有缺省值的。比如name我们可以缺省为空字符串。
这样,如果map里面没有某个值,我们就看缺省值,如果有,就用这个缺省值,如果没有,就抛异常。

手工做的话,大概是这样:
[code]
String idValue = map.get("id");
if (idValue == null) {
throw ...;
}
int id = Integer.parseInt(idValue);

String name = map.get("name");
if (name == null) {
name = "";
}

String sexValue = map.get("sex");
if (sexValue == null) {
throw ...;
}
Gender sex = Gender.valueOf(sexValue);
...
[/code]

比较痛苦。于是做了一个动态代理:
[code]
public final class PropertyConverter<T> {
private final Class<T> targetType;

private PropertyConverter(Class<T> targetType) {...}

public static <T> PropertyConverter<T> to(Class<T> targetType) {
return new PropertyConverter<T>(targetType);
}

public T from(final Map<String, String> map) {
return Proxy.newProxyInstance(
new Class[]{targetType}, targetType.getClassLoader(), new InvocationHandler() {
public Object invoke(Object proxy, Method method, Object[] args) {
String value = map.get(method.getName());
if (value == null) {
Object defaultValue = method.getDefaultValue();
if (defaultValue == null) {
throw ...;
}
return defaultValue;
}
return convert(value, method.getReturnType());
}
});
}
}
[/code]

convert()函数是调用apache的ConvertUtilsBean做的,没什么说的。

那么,用法呢?

[code]
@interface Foo {
int id();
String name() default "";
Gender sex();
}

Map<String, String> map = ...;
Foo foo = PropertyConverter.to(Foo.class).from(map);
foo.id();
foo.name();
[/code]

这里面,对annotation的用法比较特别。不过不这么做,java也不提供一个简单并且类型安全的指定缺省值的方法。当然,如果你凑巧不需要缺省值,那么也不用annotation,直接用interface就好。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值