XStream實現xml和java物件之間的互相轉換(包括對屬性,別名,下劃線_的處理),同理JSON也可以

chiweitree發表於2014-08-29

首先去官網下載響應JAR包

http://xstream.codehaus.org/index.html

最少需要兩個jar包,一個xstream.jar,一個是xmlpull.jar

首先來看下java物件到xml的轉換

 

package xml;

class PhoneNumber {
	
	private int code;
	
	private int number;

	public int getCode() {
		return code;
	}

	public void setCode(int code) {
		this.code = code;
	}

	public int getNumber() {
		return number;
	}

	public void setNumber(int number) {
		this.number = number;
	}
	
}

public class Person {

	private String username;
	
	private int age;
	
	private PhoneNumber pn;

	public String getUsername() {
		return username;
	}

	public void setUsername(String username) {
		this.username = username;
	}

	public int getAge() {
		return age;
	}

	public void setAge(int age) {
		this.age = age;
	}

	public PhoneNumber getPn() {
		return pn;
	}

	public void setPn(PhoneNumber pn) {
		this.pn = pn;
	}
	
}


以上是一個普通的java物件

 

 

package xml;

import com.thoughtworks.xstream.XStream;
import com.thoughtworks.xstream.io.xml.StaxDriver;

public class XmlUtils {

	private static XStream xs = new XStream(new StaxDriver());
	
	public static String objToXml(Object obj) {
		//xs.aliasPackage(name, pkgName);
		return xs.toXML(obj);
	}
	
	public static void main(String[] args) {
		Person p = new Person();
		p.setAge(26);
		p.setUsername("chiwei");
		PhoneNumber pn = new PhoneNumber();
		pn.setCode(188);
		pn.setNumber(67101080);
		p.setPn(pn);
		xs.alias("person", Person.class);
		String xml = objToXml(p);
		Person per = (Person)xs.fromXML(xml);
		System.out.println(xml);
		System.out.println(per.getUsername());
	}
}


以上程式碼,先是生成一個物件,給各個屬性賦值,然後呼叫toXML將物件轉換為xml格式的普通文字,注意在轉換前呼叫了alias目的是為了將xml.Person重新命名為person

 

<?xml version="1.0" ?><person><username>chiwei</username><age>26</age><pn><code>188</code><number>67101080</number></pn></person>

這裡xstream例項化時候傳入了StaxDriver表示A driver using the StAX API to create XML reader and writer.

如果你使用xpp3driver,你需要引入該jar包

後面則根據上面轉換後的xml繼續轉換成相應的物件Person

<?xml version="1.0" ?><person><username>chiwei</username><age>26</age><pn><code>188</code><number>67101080</number></pn></person>
chiwei

 

很簡單

 

 

xs.alias("person", Person.class);
		xs.useAttributeFor(Person.class,"username");
		xs.aliasAttribute(Person.class, "username","name");

這種情況是將屬性寫到XML元素的裡面作為屬性,而不是單獨作為一個子元素,如下所示:
<person name="chiwei">
  <age>26</age>
</person>
 

 

-------------------------------------------------------------------------------華麗的分割線-------------------------------------------------------------------------------------------

以上的例子的確很簡單,下面看看一些別的處理

 

xs.aliasField("res_type", SLIR.class, "resType");

該方法是用於將SLIR類中的resType屬性在XML元素中顯示為res_type,這裡看到有一個下劃線_,其實在xstream例項化的時候,如果沒有用到XmlFriendlyNameCoder的話,可能下劃線_就會變成__,因為在這裡_其實是轉移符,所以我們例項化xstream的時候應該如下:

 

 

private static XStream xs = new XStream(new DomDriver(null,new XmlFriendlyNameCoder("_-", "_")));

 

 

xs.useAttributeFor(RequestMode.class, "type");

該方法的目的是將RequestMode類中的type屬性作為該XML元素的內部屬性

<requestmode type="PASSIVE"/>

 

最後再來看下,XML元素同時又屬性和值得時候怎麼處理

 

<msid enc="ASC" type="MSISDN">13505602768</msid>

如上所示,msid元素擁有兩個屬性,同時又擁有自己的值,這時候,在做轉化的時候,必須自定義轉換器converter才行

 

 


import com.thoughtworks.xstream.converters.Converter;
import com.thoughtworks.xstream.converters.MarshallingContext;
import com.thoughtworks.xstream.converters.UnmarshallingContext;
import com.thoughtworks.xstream.io.HierarchicalStreamReader;
import com.thoughtworks.xstream.io.HierarchicalStreamWriter;

public class ReqMsidConverter implements Converter {

	@SuppressWarnings("rawtypes")
	@Override
	public boolean canConvert(Class type) {
		// TODO Auto-generated method stub
		return type.equals(Msid.class);
	}

	@Override
	public void marshal(Object source, HierarchicalStreamWriter writer,
			MarshallingContext context) {
		// TODO Auto-generated method stub
		Msid msid = (Msid)source;
		writer.addAttribute("enc", msid.getEnc());
		writer.addAttribute("type", msid.getType());
		writer.setValue(msid.getMsid());
	}

	@Override
	public Object unmarshal(HierarchicalStreamReader reader,
			UnmarshallingContext context) {
		// TODO Auto-generated method stub\
		Msid msid = new Msid();
		msid.setEnc(reader.getAttribute("enc"));
		msid.setType(reader.getAttribute("type"));
		msid.setMsid(reader.getValue());
		return msid;
	}

}

定義完該轉換器後,將其註冊到xstream上即可

 

 

xs.registerConverter(new ReqMsidConverter());

 

List列表資料的轉換

public static String obj2XML(Object obj) {
		xs.alias("InterBOSS", InterBOSS.class);
		xs.aliasField("SvcCont", InterBOSS.class, "svcCont");
		xs.aliasField("OrderInfoRsp", SvcCont.class,"orderInfoRsp");
		xs.aliasField("FileStatus", SvcCont.class,"fileStatus");
		xs.aliasField("RecNum", OrderInfoRsp.class,"recNum");
		xs.aliasField("SuccNum", OrderInfoRsp.class,"succNum");
		xs.aliasField("FailNum", OrderInfoRsp.class,"failNum");
		xs.addImplicitArray(OrderInfoRsp.class, "pmList", ProductMember.class);
		xs.alias("ProductMember", ProductMember.class);
		xs.aliasField("MemberNumber", ProductMember.class,"memberNumber");
		xs.aliasField("ProductOrderInfo", ProductMember.class,"productOrderInfo");
		xs.aliasField("Extend", ProductMember.class,"extend");
		xs.aliasField("RspCode", ProductMember.class,"rspCode");
		xs.aliasField("RspDesc", ProductMember.class,"rspDesc");
		return xs.toXML(obj);
	}

這裡的列表就是ProductMember這個元素,它有多個,這裡就注意需要使用一個api-->addImplicitArray

 


 

 

 

 

 

 

 

 

 

相關文章