Java库通过bean </string,>读取/写入Map <string,string =“”>

时间:2012-07-23 20:34:56

标签: java

我正在寻找一个库,它通过代理的Java bean提供对Map<String, String>的类型类型安全的读写访问。例如:

interface Person {
  String getName();
  void setName(String name);
  int getAge();
  void setAge(int age);
}

Map<String, String> data = new HashMap<String, String>() {{
  put("name", "juni");
  put("age", "4");
}}

Person p = HypotheticalLibrary.bind(Person.class, data);
p.getName(); // returns "juni"
p.setAge(5); // calls data.put("age", "5") --- notice the implicit type conversion

有这样的事吗?

3 个答案:

答案 0 :(得分:1)

我不知道一个。但是,使用proxy编写一个相当简单。您需要编写一个识别getter和setter的InvocationHandler,并相应地获取或放置地图。有一个小巧的位 - 将方法名称转换为地图的键 - 以及一个硬位 - 确定如何转换类型。

我在大约60行代码中写了一个快速而又脏的实现。它在类型上做了相当笨拙的工作;所有基本类型都需要另外一百左右才能完成一项体面的工作。

答案 1 :(得分:1)

假设您可以使用spring作为依赖项,可以按照建议使用代理方法。 BeanUtils类负责将方法名称转换为属性描述符,以便获取名称。不需要进行类型转换,因为您正在使用接口本身,因此编译器将确保您发送正确的类型(因此输出正确的类型)。

static interface Person {
    void setName(String name);
    String getName();
    void setAge(int age);
    int getAge();
}


public static Person createPerson() {
    return createPerson(new HashMap<String, String>());
}

public static Person createPerson(final Map<String, String> props) {
    InvocationHandler ih = new InvocationHandler() {
        private TypeConverter typeConverter = new SimpleTypeConverter();

        @Override
        public Object invoke(Object source, Method method, Object[] params)
                throws Throwable {
            PropertyDescriptor pd = BeanUtils.findPropertyForMethod(method);
            if (method.getName().startsWith("set")) {
                props.put(pd.getName(), typeConverter.convertIfNecessary(params[0], String.class));
                return null;
            }
            else if (method.getName().startsWith("get") ||
                     method.getName().startsWith("is")) {
                Object res = props.get(pd.getName());
                return typeConverter.convertIfNecessary(res, method.getReturnType());
            }
            return null;
        }
    };

    Person p = (Person) Proxy.newProxyInstance(Thread.currentThread().getContextClassLoader(),
            new Class<?>[] { Person.class },
            ih);

    return p;
}

public static void main(String args[]) {
    final Map<String, String> props = new HashMap<String, String>();
    props.put("name", "Matt");
    props.put("age", "4");

    Person p = createPerson(props);

    System.out.println(p.getName());
    System.out.println(p.getAge());

}

答案 2 :(得分:0)

我不相信有一个,但你可以在mvelognlspel的帮助下建立自己的自己。我确实在某个时候建立了自己的。