XmlAdapter

jaxb对Map的处理很简单粗暴

package com.test;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;

import javax.xml.bind.JAXBContext;
import javax.xml.bind.Marshaller;
import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlElementWrapper;
import javax.xml.bind.annotation.XmlRootElement;

@XmlRootElement(name="MyRootElement")
public class XmlAdapter {
    @XmlElement
    @XmlElementWrapper(name="People")
    private Map<Integer, String> people = new HashMap<>();
    
    
    public static void main(String[] args) throws Exception {
        XmlAdapter root = new XmlAdapter();
        
        root.getPeople().put(1, "One");
        root.getPeople().put(2, "Two");
        root.getPeople().put(3, "Three");
        
        JAXBContext context = JAXBContext.newInstance(XmlAdapter.class);
        Marshaller m = context.createMarshaller();
        m.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE);
        m.marshal(root, System.out);
    }


    public Map<Integer, String> getPeople() {
        return people;
    }   
}

输出如下。估计没有人会用这种XML schema

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<MyRootElement>
    <People>
        <entry>
            <key>1</key>
            <value>One</value>
        </entry>
        <entry>
            <key>2</key>
            <value>Two</value>
        </entry>
        <entry>
            <key>3</key>
            <value>Three</value>
        </entry>
    </People>
</MyRootElement>

用XmlAdapter可以自定义绑定.

package com.test;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.xml.bind.JAXBContext;
import javax.xml.bind.Marshaller;
import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlAccessorType;
import javax.xml.bind.annotation.XmlAttribute;
import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlRootElement;
import javax.xml.bind.annotation.XmlValue;
import javax.xml.bind.annotation.adapters.XmlAdapter;
import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter;

@XmlRootElement(name="MyRootElement")
@XmlAccessorType(XmlAccessType.FIELD)
public class XmlAdapter2 {
    @XmlElement(name="mypeoplemap")
    @XmlJavaTypeAdapter(MyMapAdapter.class)
    private Map<Integer, String> peopleMap = new HashMap<>();
    
    
    public static void main(String[] args) throws Exception {
        XmlAdapter2 root = new XmlAdapter2();
        
        root.getPeopleMap().put(1, "One");
        root.getPeopleMap().put(2, "Two");
        root.getPeopleMap().put(3, "Three");
        
        JAXBContext context = JAXBContext.newInstance(XmlAdapter2.class);
        Marshaller m = context.createMarshaller();
        m.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE);
        m.marshal(root, System.out);
        
    }


    public Map<Integer, String> getPeopleMap() {
        return peopleMap;
    }
    
}
@XmlAccessorType(XmlAccessType.FIELD)
class People {  
    @XmlAttribute
    private Integer id;
    @XmlValue
    private String name;
    public Integer getId() {
        return id;
    }
    public void setId(Integer id) {
        this.id = id;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
}
@XmlAccessorType(XmlAccessType.FIELD)
class PeopleList {
    @XmlElement(name="people")
    private List<People> peopleList = new ArrayList<>();;

    public List<People> getPeopleList() {
        return peopleList;
    }

}
class MyMapAdapter extends XmlAdapter<PeopleList, Map<Integer, String>> {

    @Override
    public PeopleList marshal(Map<Integer, String> peopleMap) throws Exception {
        
        PeopleList peopleList = new PeopleList();
        for (Integer key: peopleMap.keySet()) {
            People p = new People();
            p.setId(key);
            p.setName(peopleMap.get(key));
            peopleList.getPeopleList().add(p);
        }
        return peopleList;
    }

    @Override
    public Map<Integer, String> unmarshal(PeopleList peopleList) throws Exception {
        Map<Integer, String> map = new HashMap<>();
        for (People p: peopleList.getPeopleList()) {
            map.put(p.getId(), p.getName());
        }
        return map;
    }
    
}

输出

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<MyRootElement>
    <mypeoplemap>
        <people id="1">One</people>
        <people id="2">Two</people>
        <people id="3">Three</people>
    </mypeoplemap>
</MyRootElement>

为了这种格式的输出,写了3个辅助类。一个代表map的entry的类People,一个类似容器的PeopleList类,还有一个adapter类。真正干活的是adapter类。另外还要注意要用@XmlJavaTypeAdapter注册这个adapter类

public class XmlAdapter2 {
    @XmlElement(name="mypeoplemap")
    @XmlJavaTypeAdapter(MyMapAdapter.class)
    private Map<Integer, String> peopleMap = new HashMap<>();
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容