Java 使用JAXB解组具有相同名称的XML标记
我遇到了一个棘手的问题,我应该使用JAXB库解组XML输入流,但XML结构没有帮助 我的问题是:Java 使用JAXB解组具有相同名称的XML标记,java,xml,jaxb,xsd,Java,Xml,Jaxb,Xsd,我遇到了一个棘手的问题,我应该使用JAXB库解组XML输入流,但XML结构没有帮助 我的问题是:item标记用于具有值的简单元素,或用于其他“items”的列表 下面是一个简单的XML: <root> <item label="This is a LIST item" type="list"> <item label="This is a VALUE item" type="string">Value</item>
item
标记用于具有值的简单元素,或用于其他“items”的列表
下面是一个简单的XML:
<root>
<item label="This is a LIST item" type="list">
<item label="This is a VALUE item" type="string">Value</item>
</item>
</root>
一个项目
唯一能告诉我的是一个列表,它的类型
属性总是有一个值
我尝试了一些方法,但无法成功地正确编写Java类来解码。我不知道这是否可以告诉Jaxb标签可能是列表或元素
我甚至尝试用另一个项目替换这个项目/列表标记,但很难找到结束标记
当然,我不能改变这种结构,这不在我手中。
有人有办法处理这种结构吗?我建议您使用这种解决方案。通过这种方式,您可以根据需要添加任意多的级别
Root.java
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "root", propOrder = {
"items"
})
@XmlRootElement(name = "root")
public class Root
implements Serializable
{
private final static long serialVersionUID = 1234567890L;
@XmlElement(name = "item")
protected List<Item> items;
/**
* Gets the value of the items property.
*
* <p>
* This accessor method returns a reference to the live list,
* not a snapshot. Therefore any modification you make to the
* returned list will be present inside the JAXB object.
* This is why there is not a <CODE>set</CODE> method for the items property.
*
* <p>
* For example, to add a new item, do as follows:
* <pre>
* getItems().add(newItem);
* </pre>
*
*
* <p>
* Objects of the following type(s) are allowed in the list
* {@link Item }
*
*
*/
public List<Item> getItems() {
if (items == null) {
items = new ArrayList<Item>();
}
return this.items;
}
}
<xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="root" type="root" />
<xs:complexType name="root">
<xs:sequence>
<xs:element name="item" type="item" minOccurs="0" maxOccurs="unbounded" />
</xs:sequence>
</xs:complexType>
<xs:element name="item" type="item" />
<xs:complexType name="item" mixed="true">
<xs:sequence>
<xs:any maxOccurs="unbounded" />
</xs:sequence>
<xs:attribute type="xs:string" name="num" use="optional" />
<xs:attribute type="xs:string" name="label" use="optional" />
<xs:attribute type="xs:string" name="type" use="optional" />
</xs:complexType>
</xs:schema>
*
*
*
*列表中允许以下类型的对象
*{@link Item}
*
*
*/
公共列表getItems(){
if(items==null){
items=newarraylist();
}
归还此物品;
}
}
Item.java
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "root", propOrder = {
"items"
})
@XmlRootElement(name = "root")
public class Root
implements Serializable
{
private final static long serialVersionUID = 1234567890L;
@XmlElement(name = "item")
protected List<Item> items;
/**
* Gets the value of the items property.
*
* <p>
* This accessor method returns a reference to the live list,
* not a snapshot. Therefore any modification you make to the
* returned list will be present inside the JAXB object.
* This is why there is not a <CODE>set</CODE> method for the items property.
*
* <p>
* For example, to add a new item, do as follows:
* <pre>
* getItems().add(newItem);
* </pre>
*
*
* <p>
* Objects of the following type(s) are allowed in the list
* {@link Item }
*
*
*/
public List<Item> getItems() {
if (items == null) {
items = new ArrayList<Item>();
}
return this.items;
}
}
<xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="root" type="root" />
<xs:complexType name="root">
<xs:sequence>
<xs:element name="item" type="item" minOccurs="0" maxOccurs="unbounded" />
</xs:sequence>
</xs:complexType>
<xs:element name="item" type="item" />
<xs:complexType name="item" mixed="true">
<xs:sequence>
<xs:any maxOccurs="unbounded" />
</xs:sequence>
<xs:attribute type="xs:string" name="num" use="optional" />
<xs:attribute type="xs:string" name="label" use="optional" />
<xs:attribute type="xs:string" name="type" use="optional" />
</xs:complexType>
</xs:schema>
*
*
*
*列表中允许以下类型的对象
*{@link String}
*{@link Object}
*
*
*/
公共列表getContent(){
if(content==null){
content=newarraylist();
}
返回此.content;
}
/**
*恢复正常生活。
*
*@返回
*可能的对象是
*{@link String}
*
*/
公共字符串getNum(){
返回num;
}
/**
*财产税。
*
*@param值
*允许的对象是
*{@link String}
*
*/
公共void setNum(字符串值){
this.num=值;
}
/**
*重新使用标签。
*
*@返回
*可能的对象是
*{@link String}
*
*/
公共字符串getLabel(){
退货标签;
}
/**
*商标税。
*
*@param值
*允许的对象是
*{@link String}
*
*/
公共void setLabel(字符串值){
this.label=值;
}
/**
*以适当的方式复发。
*
*@返回
*可能的对象是
*{@link String}
*
*/
公共字符串getType(){
返回类型;
}
/**
*不可抗力类型。
*
*@param值
*允许的对象是
*{@link String}
*
*/
公共void集合类型(字符串值){
this.type=值;
}
}
我用过这个XSD
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<root>
<item label="This is a LIST item" type="List">
<item label="Upper" type="string">ABC</item>
<item label="Lower" type="string">abc</item>
<item num="1" type="list">
<item label="a" type="other">aaaaa</item>
</item>
</item>
</root>
输出
基础知识
abc
AAAA
第一个问题是:有多少级别的物品?这是一个有限的级别数吗?非常好的答案,我很感激编写这么多代码来帮助某人。我会将@XmlMixed
注释与@xmlementref
配对,而不是@xmlanyement
来控制可以进入列表的内容。非常感谢,它确实使用从给定XSD生成的类来解码XML。但是,我得到了一个对象列表,包括Item(good)和String=“\n\t\t”。。!是否可以跳过这些字符?我猜“为了避免\n\t等,好吧,我同意这个答案,因为它正确地解组了XML,我非常感谢您的非常详细的回答!但是这个解决方案对我来说不是最好的,因为我现在得到的是Jaxb元素的列表
,而不是项的列表
。这在Java代码中处理起来非常难看…:/
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<root>
<item label="This is a LIST item" type="List">
<item label="Upper" type="string">ABC</item>
<item label="Lower" type="string">abc</item>
<item num="1" type="list">
<item label="a" type="other">aaaaa</item>
</item>
</item>
</root>