xstream读取xml

xStream可以Java和xml相互转换。下面主要说明xstream读取xml文件(和xstream将Java转化成xml差不多)。本次学习用到的是xstream1.4.7

项目中使用到的xml文件


<config name="personconfig">
<!-- <add> --> <!-- 使用addImplicitCollection可以不出现 -->
<address>
<add>abc;abc</add>
<zipcode>zip#efg</zipcode>
</address>
<address>
<add>abcfe;123</add>
<zipcode>zipaf#695</zipcode>
</address>
<!-- </add> -->
</config>

保存xml的Java类,其中add存储xml里的所有Address节点信息。

对于不是用注解方式的:


package com.core;

import java.util.ArrayList;
import java.util.List;

public class Person {
private String name;

/**
* add名称必须和包含Address的父节点一致,否则数据读取失败(除非使用了addImplicitCollection,则可以不出现<add>
*/
public List<Address> add = new ArrayList<Address>();

public String getName() {
return name;
}

public class Address {
private String add; //不一定要给出get/set方法,没有仍然可以从xml读取,这里给出get是因为要读取数据
private String zipcode;
public String getAdd() {
return add;
}
public String getZipcode() {
return zipcode;
}

}

}

读取xml主类:


package com.core;

import java.io.InputStream;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import com.core.Person.Address;
import com.thoughtworks.xstream.XStream;
import com.thoughtworks.xstream.io.xml.DomDriver;

public class XStreamUtils {
private String fileName = "xstream.xml";

public XStreamUtils() {
XStream xstream = new XStream(new DomDriver()); //还可以使用new StaxDriver(),官网推荐xpp3(最快解析xml,但是对于解析程序的配置文件,一般DomDriver和StaxDriver都够了)

//指明类与xml里的element对应关系,如果不指明,则element必须详细到类,如<com.core.Person>
xstream.alias("address", Address.class);
xstream.alias("config", Person.class);

xstream.useAttributeFor(Person.class,"name"); //读取element attribute配置
//the addImplicitCollection method call: it describes which class and which member variable shall assume the behaviour we described.
xstream.addImplicitCollection(Person.class, "add"); //此声明可以使得address的父节点不需要出现<add>
InputStream in = Thread.currentThread().getContextClassLoader().getResourceAsStream(fileName);
Person p = (Person) xstream.fromXML(in);
System.out.println(p.add.get(1).getZipcode());
System.out.println(p.getName());
}

public static void main(String[] args) {
XStreamUtils x = new XStreamUtils();
}
}

注:如果要xml要映射到的Java类里有list的属性(如上面的public List<Address>
add),如果address的父节点没有add,而代码里没有使用

addImplicitCollection(Person.class, "add"),则程序会抛出异常。
xstream不要求xml对应的Java类的属性一定要有get和set方法,没有也是可以成功的(估计是用了反射)。

2.使用注解:


package com.annotations;

import java.util.ArrayList;
import java.util.List;

import com.thoughtworks.xstream.annotations.XStreamAlias;
import com.thoughtworks.xstream.annotations.XStreamAsAttribute;
import com.thoughtworks.xstream.annotations.XStreamConverter;
import com.thoughtworks.xstream.annotations.XStreamImplicit;

/**
* 使用Java annotation
* @author
*
*/
@XStreamAlias("config") //声明在xml中的节点名称
public class Person {

@XStreamAsAttribute //说明这个值是取自节点attribute
private String name;

@XStreamImplicit //Address节点父节点无需是add
public List<Address> add = new ArrayList<Address>();

public String getName() {
return name;
}

@XStreamAlias("address")
public class Address {
//操作add子节点的内容,将结果放入add中
@XStreamConverter(value= SplitConverter.class,strings={";"})
private List<String> add; // 不一定要给出get/set方法,没有仍然可以从xml读取,这里给出get是因为要读取数据

@XStreamConverter(value= SplitConverter.class,strings={"#"})
private List<String> zipcode;

public void toAddressList() {
System.out.println("address start" + add.size());
for(String s : add) {
System.out.print(s + "\t");
}
System.out.println("address end");
}

public void toZipCodeList() {
System.out.println("zipcode start" + zipcode.size());
for(String s : zipcode) {
System.out.print(s + "\t");
}
System.out.println("zipcode end");
}

}

}

SplitConverter实现(Converter可以将xml里某个节点的内容根据需要转换成Java类里面需要的类型,反之亦然。可以使用

 @XStreamConverter(value= SplitConverter.class,strings={";"}来重用converter):
SplitConverte作用:将某个节点的内容按照给定的分割符分割。


package com.annotations;

import java.util.ArrayList;
import java.util.List;

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;

/**
* 将某个节点的数据根据已给的分割符进行分割
* @author
*
*/
public class SplitConverter implements Converter {

private String partionSymbol;

public SplitConverter() {
super();
}

public SplitConverter(String str) {
super();
this.partionSymbol = str;
}

/**
* 判断是否可以convert
*/
@Override
public boolean canConvert(Class arg0) {
// TODO Auto-generated method stub
return true;
}

/**
* 写xml时,Java属性特殊处理
*/
@Override
public void marshal(Object arg0, HierarchicalStreamWriter arg1,
MarshallingContext arg2) {
// TODO Auto-generated method stub

}

/**
* 读取xml数据时对某个节点的数据操作
*/
@Override
public Object unmarshal(HierarchicalStreamReader reader,
UnmarshallingContext arg1) {
// TODO Auto-generated method stub
List<String> list = null;
String content = reader.getValue();
String[] arr = content.split(this.partionSymbol);
if(null != arr) {
list = new ArrayList<String>(arr.length);
for(String s : arr) {
list.add(s);
}
}
return list;
}

}

注解 Main类:


package com.annotations;

import java.io.InputStream;

import com.annotations.Person.Address;
import com.thoughtworks.xstream.XStream;
import com.thoughtworks.xstream.io.xml.DomDriver;

public class AnnotationMain {

private String fileName = "xstream.xml";

public AnnotationMain() {
XStream xstream = new XStream(new DomDriver());
//说明注解了哪些些类
xstream.processAnnotations(Person.class);
xstream.processAnnotations(Address.class);
InputStream in = Thread.currentThread().getContextClassLoader().getResourceAsStream(fileName);
Person p = (Person) xstream.fromXML(in);
p.add.get(0).toAddressList();
p.add.get(1).toZipCodeList();
}

public static void main(String[] args) {
// TODO Auto-generated method stub
AnnotationMain a = new AnnotationMain();
}

}

附:

Xstream常用注解: 
@XStreamAlias("message")

别名注解

作用目标: 类,字段

@XStreamImplicit

隐式集合

@XStreamImplicit(itemFieldName="subElementName")  
作用目标:

集合字段

@XStreamConverter(SingleValueCalendarConverter.class)  
 //不传入参数的

注入转换器  
作用目标: 对象

@XStreamAsAttribute 转换成属性  
作用目标:
字段

@XStreamOmitField 忽略字段  
作用目标: 字段

此次学习时的测试项目在:http://pan.baidu.com/s/1tjzNC

xstream读取xml,布布扣,bubuko.com

时间: 2024-08-24 07:45:43

xstream读取xml的相关文章

XStream解析XML文本并用反射机制转换为对象

xml文本格式是网络通信中最常用的格式,最近特别研究了一下如何解析xml文本并转换为对象,现在分享一下我最近的学习成果~ 先列一下本例中需要解析的xml文本: Xml代码   <results name="list"> <row pubtime="2016-04-13 16:40:13" author="APP"  id="140" title="什么是公告" content="

android XMLPullParser读取xml文件

由于刚学Android,用的开发工具是Android studio,没用过eclipse的那个开发Android,所以针对有些说由于2个IDE的路径不通导致的文件读取不到,不做分析(实际上是没法分析eclipse里的),这个博文只针对AS用户. 我们的资源文件,除了放到res目录下之外,还可以放在跟java .res同级的asserts(新建的)目录里. 今天要解析的这个xml就是在这个目录下的. 首先说一下xmlpullparser,这个pull解析是基于事件的模式.比如 读取到xml的开始声

C#读取XML文件的基类实现

刚到新单位,学习他们的源代码,代码里读写系统配置文件的XML代码比较老套,直接写在一个系统配置类里,没有进行类的拆分,造成类很庞大,同时,操作XML的读写操作都是使用SetAttribute和node.Attribute(name)方法,因此,想到结合之前所做的XML操作,完成了一个能够读取XML文件的基类,便于以后的使用. PS:即使再老套的代码,目前也不敢进行优化,一是水平不行,二是不敢. 使用静态扩展类,扩展了几个经常使用的类型,能够方便数据的读写. 操作XML的类,可以直接继承BaseL

【XML配置文件读取】使用jdom读取XML配置文件信息

在项目中我们经常需要将配置信息写在配置文件中,而XML配置文件是常用的格式. 下面将介绍如何通过jdom来读取xml配置文件信息. 配置文件信息 <?xml version="1.0" encoding="UTF-8"?> <config> <base-config> <stringValue>Hello world</stringValue> <integerValue>8</integ

C#中使用XML指南之读取XML

? C#中使用XML指南之读取XML ? 访问的两种模型: ? 在程序中访问进而操作XML文件一般有两种模型,分别是使用DOM(文档对象模型)和流模型,使用DOM的好处在于它允许编辑和更新XML文档,可以随机访问文档中的数据,可以使用XPath查询,但是,DOM的缺点在于它需要一次性的加载整个文档到内存中,对于大型的文档,这会造成资源问题.流模型很好的解决了这个问题,因为它对XML文件的访问采用的是流的概念,也就是说,任何时候在内存中只有当前节点,但它也有它的不足,它是只读的,仅向前的,不能在文

用C#读取XML文档

本文将以一个非常简单的例子来说明如何使用C#访问一个XML文件并且读取其中的信息.例子本身并无任何实际意义,它只是简单的介绍了如何调用微软的XML标准以及如何运用到实际当中去.希望能够对初次接触C#或者未尝试过通过C#读取XML文件的读者有所启发.本文旨在抛砖引玉,希望能与更多的朋友交流和分享经验.    制作过程 1. 运行Visual Studio.NET,新建Visual C#.NET工程,这里取名为ReadXML. 2. 在解决方案资源管理器中,将Form1.cs改名为frmAuthor

读取xml并将节点保存到Excal

using NPOI.HPSF; using NPOI.HSSF.UserModel; using NPOI.SS.UserModel; using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; using System.Drawing; using System.IO; using System.Linq; using System.Text; using Sy

Excel开发学习笔记:读取xml文件及csv文件

读取xml文件 有好多种读取xml的方式,xmlDOM比较常见,我使用了另外一种,它以数据流的方式打开文件并读取内容 Imports System.Xml  Dim group As New List(Of String)  Using reader As XmlReader = XmlReader.Create(OpenFileDialog2.FileName)      While reader.ReadToFollowing("group")          reader.Mo

C# 递归读取XML菜单数据

在博客园注册了有4年了,很遗憾至今仍未发表过博客,趁周末有空发表第一篇博客.小生不才,在此献丑了! 最近在研究一些关于C#的一些技术,纵观之前的开发项目的经验,做系统时显示系统菜单的功能总是喜欢把数据写在数据库表,然后直接读取加载到菜单树上显示. 现在想把菜单数据都放在XML里,然后递归读取XML. 由于项目使用WCF,实体类使用了两个,一个是业务逻辑层中的实体,一个是调用业务逻辑层递归方法后进行数据实体的转换,XML读取方法写在业务逻辑层中. 思路:1.先读取XML里所有的菜单    2.根据