1. 程式人生 > >多層map、xml相互轉換

多層map、xml相互轉換

程式碼主要匯入的jar為dom4j,程式碼有註釋,我就不解釋了。


import java.io.IOException;
import java.io.StringReader;
import java.io.StringWriter;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;


import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.DocumentHelper;
import org.dom4j.Element;


/**
 * 
 * 提供Map<String,Object>轉XML,XML轉Map<String,Object>
 * 
 * @author MOSHUNWEI
 * @since 2018-03-09
 * @version 5.0
 */


public class XmlMap {


	/**
	 * 
	 * 通過Map建立XML,Map可以多層轉換
	 * 
	 * @param params
	 * @return	String-->XML
	 */
	public static String createXmlByMap(String parentName,Map<String, Object> params,boolean isCDATA){
		Document doc = DocumentHelper.createDocument();
		doc.addElement(parentName);
		String xml = iteratorXml(doc.getRootElement(),parentName,params,isCDATA);
		return formatXML(xml);
	}
	
	/**
	 * 
	 * 通過Map建立XML,Map可以多層轉換
	 * 可以自定義parent節點
	 * 
	 * @param params
	 * @return	String-->XML
	 */
	public static String createXmlByMap(String parentName,Map<String, Object> params){
		Document doc = DocumentHelper.createDocument();
		doc.addElement(parentName);
		String xml = iteratorXml(doc.getRootElement(),parentName,params,false);
		return formatXML(xml);
	}
	
	/**
	 * 
	 * 通過Map建立XML,Map可以多層轉
	 * 固定節點parent為Document
	 * 
	 * @param params
	 * @return	String-->XML
	 */
	public static String createXmlByMap(Map<String, Object> params){
		String parentName = "Document";
		Document doc = DocumentHelper.createDocument();
		doc.addElement(parentName);
		String xml = iteratorXml(doc.getRootElement(),parentName,params,false);
		return formatXML(xml);
	}
	
	/**
	 * 
	 * MapToXml迴圈遍歷建立xml節點
	 * 此方法在value中加入CDATA識別符號
	 * 
	 * @param element 根節點
	 * @param parentName 子節點名字
	 * @param params map資料
	 * @return String-->Xml
	 */
	
	@SuppressWarnings("unchecked")
	public static String iteratorXml(Element element,String parentName,Map<String,Object> params,boolean isCDATA) {
		Element e = element.addElement(parentName);
		Set<String> set = params.keySet();
		for (Iterator<String> it = set.iterator(); it.hasNext();) {
			String key = (String) it.next();
			if(params.get(key) instanceof Map) {
				iteratorXml(e,key,(Map<String,Object>)params.get(key),isCDATA);
			}else {
				String value = params.get(key)==null?"":params.get(key).toString();
				if(!isCDATA) {
					e.addElement(key).addText(value);	
				}else {
					e.addElement(key).addCDATA(value);	
				}
			}
		}
		return e.asXML(); 
	}
	
	/**
	 * 格式化xml,顯示為容易看的XML格式
	 * 
	 * @param inputXML
	 * @return
	 */
	public static String formatXML(String inputXML){
		String requestXML = null;
		XMLWriter writer = null;
		Document document = null;
		try {
			SAXReader reader = new SAXReader();
			document = reader.read(new StringReader(inputXML));
			if (document != null) {
				StringWriter stringWriter = new StringWriter();
				OutputFormat format = new OutputFormat("	", true);//格式化,每一級前的空格
				format.setNewLineAfterDeclaration(false);	//xml宣告與內容是否新增空行
				format.setSuppressDeclaration(false);		//是否設定xml宣告頭部
				format.setNewlines(true);		//設定分行
				writer = new XMLWriter(stringWriter, format);
				writer.write(document);
				writer.flush();
				requestXML = stringWriter.getBuffer().toString();
			}
			return requestXML;
		} catch (Exception e1) {
			e1.printStackTrace();
			return null;
		}finally {
			if (writer != null) { 
				try {
					writer.close();
				} catch (IOException e) {
					
				}
			}
		}
	}
 
	
	/** 
	 * 
	* 通過XML轉換為Map<String,Object> 
	* 
	* @param xml 為String型別的Xml
	* @return 第一個為Root節點,Root節點之後為Root的元素,如果為多層,可以通過key獲取下一層Map
	*/  
	public static Map<String, Object> createMapByXml(String xml) {
		Document doc = null;
		try {
			doc = DocumentHelper.parseText(xml);
		} catch (DocumentException e) {
			e.printStackTrace();
		}
		Map<String, Object> map = new HashMap<String, Object>();
		if (doc == null)
			return map;
		Element rootElement = doc.getRootElement();
		elementTomap(rootElement,map);
		return map;
	}
	
	/***
	 *  
	 * XmlToMap核心方法,裡面有遞迴呼叫 
	 *  
	 * @param map 
	 * @param ele 
	 */  
	@SuppressWarnings("unchecked")
	public static Map<String, Object> elementTomap (Element outele,Map<String,Object> outmap) {
		List<Element> list = outele.elements();
		int size = list.size();
		if(size == 0){
			outmap.put(outele.getName(), outele.getTextTrim());
	}else{
		Map<String, Object> innermap = new HashMap<String, Object>();
		for(Element ele1 : list){
			String eleName = ele1.getName();
			Object obj =  innermap.get(eleName);
			if(obj == null){
				elementTomap(ele1,innermap);
			}else{
				if(obj instanceof java.util.Map){
				List<Map<String, Object>> list1 = new ArrayList<Map<String, Object>>();
				list1.add((Map<String, Object>) innermap.remove(eleName));
				elementTomap(ele1,innermap);
				list1.add((Map<String, Object>) innermap.remove(eleName));
				innermap.put(eleName, list1);
			}else{
				elementTomap(ele1,innermap);
				((List<Map<String, Object>>)obj).add(innermap);
			}
		}
	}
		outmap.put(outele.getName(), innermap);
	}
	return outmap;
}
public static void main(String[] args) {
		Map<String,Object> result = new HashMap<String,Object>();
		result.put("Request", "getData");
		Map<String,Object> map = new HashMap<String,Object>();
		map.put("data", "2018-01-01");
		map.put("name", "jack");
		result.put("Data", map);
		System.out.println(createXmlByMap(result));
		System.out.println(createXmlByMap("Parent", result));
		System.out.println(createXmlByMap("Parent", result,true));
		System.out.println(createMapByXml(createXmlByMap(result)));
	}
}

結果為:

<?xml version="1.0" encoding="UTF-8"?>
<Document>
    <Request>getData</Request>
    <Data>
        <data>2018-01-01</data>
        <name>jack</name>
    </Data>
</Document>

<?xml version="1.0" encoding="UTF-8"?>
<Parent>
    <Request>getData</Request>
    <Data>
        <data>2018-01-01</data>
        <name>jack</name>
    </Data>
</Parent>

<?xml version="1.0" encoding="UTF-8"?>
<Parent>
    <Request><![CDATA[getData]]></Request>
    <Data>
        <data><![CDATA[2018-01-01]]></data>
        <name><![CDATA[jack]]></name>
    </Data>
</Parent>

{Document={Request=getData, Data={data=2018-01-01, name=jack}}}