如何使用EL表达式中的键获取EnumMap中的值?

时间:2011-08-03 08:31:31

标签: java jsp el

我有一个EnumMap:

EnumMap<Gender, Integer> genderMap = new EnumMap(Gender.class);

性别为public enum Gender {Male, Female};

我有req.setAttribute("genderMap", genderMap);

现在我想通过JSP文件中的一个键从genderMap获取值:

${genderMap['Male']}

但这不会获得genderMap中的值。为什么呢?

4 个答案:

答案 0 :(得分:0)

Map<Gender, Integer> genderMap = new HashMap<Gender, Integer>();

${genderMap['Male']}

这肯定会奏效。

答案 1 :(得分:0)

因为'Male'计算字符串“男性”,而不是Gender.Male。您需要访问Gender.Male常量才能访问其映射条目。但是在JSP EL中无法访问常量,因此您可能希望这样做:

req.setAttribute("male", Gender.Male);
req.setAttribute("genderMap", genderMap);

...

${genderMap[male]}

答案 2 :(得分:0)

不要使用枚举映射。只需使用枚举作为Java中的枚举和JSP / EL中的字符串。

由于数据库映射,我假设你需要那个整数。例如。 Male在数据库中存储为1Female在数据库中存储为0。在这种情况下,您需要按如下方式重新设计枚举:

public enum Gender {

    Male(1), Female(0);

    private int id;

    private Gender(int id) { 
        this.id = id;
    }

    public int getId() {
        return id;
    }

    public static Gender valueOf(int id) {
        for (Gender gender : values()) {
            if (gender.id == id) {
                return gender;
            }
        }

        return null;
    }

}

通过JDBC从DB填充Person时,只需执行

person.setGender(Gender.valueOf(resultSet.getInt("gender")));

在JSP中向enduser显示预选选项时,只需执行

request.setAttribute("genders", Gender.values());

Gender:<br/>
<c:forEach items="${genders}" var="gender">
    <input type="radio" id="gender_${gender.id}" name="gender" value="${gender.id}" 
        ${gender == person.gender ? 'checked="checked"' : ''} />
    <label for="gender_${gender.id}">${gender}</label>
    <br />
</c:forEach>

甚至没有id

Gender:<br/>
<c:forEach items="${genders}" var="gender">
    <input type="radio" id="gender_${gender}" name="gender" value="${gender}" 
        ${gender == person.gender ? 'checked="checked"' : ''} />
    <label for="gender_${gender}">${gender}</label>
    <br />
</c:forEach>

在servlet中收集提交的值时,只需执行

Gender gender = Gender.valueOf(Integer.valueOf(request.getParameter("gender")));

或在HTML中使用id

Gender gender = Gender.valueOf(request.getParameter("gender"));

答案 3 :(得分:0)

我的解决方案是为枚举映射创建一个包装器(适配器)。它需要String键并通过调用Enum.valueOf()方法将它们转换为相应的Enum值。

示例bean的相关部分:

private Map <Action, Permission> permissions = new EnumMap<>(Action.class);

/** For java access */
public Map<Action, Permission> getPermissions() {
    return permissions;
}

/** For EL access */
public Map<String, Permission> getPermissionsAsString() {
    return new EnumMapWrapper<>(Action.class, permissions);
}

现在我可以方便地访问EL中的地图元素:

#{rule.permissionsAsString['MODIFY']}

这是包装类:

public class EnumMapWrapper<K extends String, V> implements Map<K, V> {

    private Map<Enum, V> map;
    private Class<? extends Enum> enumType;

    public EnumMapWrapper(Class<? extends Enum> enumType, Map<? extends Enum, V> map) {
        this.enumType = enumType;
        this.map = (Map<Enum, V>)map;
    }

    private Enum valueOf(Object key) {
        if (!(key instanceof String)) {
            throw new IllegalArgumentException("Only string keys are permitted");
        }

        return Enum.valueOf(enumType, (String)key);
    }

    @Override
    public int size() {
        return map.size();
    }

    @Override
    public boolean isEmpty() {
        return map.isEmpty();
    }

    @Override
    public boolean containsKey(Object key) {
        return map.containsKey(valueOf(key));
    }

    @Override
    public boolean containsValue(Object value) {
        return map.containsValue(value);
    }

    @Override
    public V get(Object key) {
        return map.get(valueOf(key));
    }

    @Override
    public V put(K key, V value) {
        return map.put(valueOf(key), value);
    }

    @Override
    public V remove(Object key) {
        return map.remove(valueOf(key));
    }

    @Override
    public void putAll(Map<? extends K, ? extends V> m) {
        throw new UnsupportedOperationException();
    }

    @Override
    public void clear() {
        map.clear();
    }

    @Override
    public Set<K> keySet() {
        throw new UnsupportedOperationException();
    }

    @Override
    public Collection<V> values() {
        return map.values();
    }

    @Override
    public Set<Entry<K, V>> entrySet() {
        throw new UnsupportedOperationException();
    }
}