Просто начинайте работу с JAXB сегодня, и я застрял на нечетном представлении списка элементов данных, когда есть только одно значение. Обратите внимание, что для одиночных значений colors
он рассматривается скорее как элемент вместо списка и не обернут в тег color
. Данные поступают из внешнего источника, и я не контролирую форматирование.JAXB Parsing Wrapper с одним текстовым элементом вместо XmlElement
Как JAXB может иметь дело с обоими представлениями colors
?
<?xml version="1.0" encoding="utf-8"?>
<widgets>
<widget>
<name>SingleValue</name>
<colors>Blue</colors>
</widget>
<widget>
<name>ListValues</name>
<colors>
<color>Red</color>
<color>Blue</color>
</colors>
</widget>
</widgets>
Я пробовал различные попытки с комбинациями @XmlElementWrapper
и @XmlElement
, @XmlAnyElements
, @XmlElementRef(s)
и @XmlMixed
. Я даже создал класс цветов и попробовал несколько сопоставлений массивам и строкам без везения; они будут работать индивидуально, но не при использовании одновременно.
Использование примера XML выше, вот простая программа, которая бы правильно проанализировала «Синий», если бы она была обернута в теги color
. В настоящее время эта программа возвращает пустой список для цветов и не может выбрать «Синий».
@XmlRootElement(name = "widgets")
@XmlAccessorOrder(XmlAccessOrder.UNDEFINED)
public class Widgets {
private List<Widget> widgets = new ArrayList<Widget>();
public static void main(String[] args) {
File f = new File("C:\\aersmine\\AERS_KDR_Data", "widgets.xml");
try {
Widgets widgets = Widgets.load(f);
for (Widget widget : widgets.widgets) {
StringBuilder sb = new StringBuilder();
for (String color : widget.getColors()) {
if (sb.length() > 0)
sb.append(", ");
sb.append(color);
}
System.out.println("Widget " + widget.getName() + " Colors: " + sb.toString());
}
}
catch (Exception e) {
e.printStackTrace();
}
}
public static Widgets load(File file)
throws JAXBException, IOException {
FileInputStream is = new FileInputStream(file);
try {
JAXBContext ctx = JAXBContext.newInstance(Widgets.class);
Unmarshaller u = ctx.createUnmarshaller();
return (Widgets) u.unmarshal(is);
}
finally {
is.close();
}
}
@XmlElement(name="widget")
public List<Widget> getWidgets() {
return widgets;
}
public void setWidgets(List<Widget> widgets) {
this.widgets = widgets;
}
}
public class Widget {
public String n;
public List<String> cl = new ArrayList<String>();
@XmlElement(name="name")
public String getName() {
return n;
}
public void setName(String name) {
this.n = name;
}
@XmlElementWrapper(name="colors")
@XmlElement(name="color")
public List<String> getColors() {
return cl;
}
public void setColors(List<String> colors) {
this.cl = colors;
}
}
Большое спасибо за помощь.
Я отмечаю это как ответ, учитывая, что я никогда не находил разумного решения. Учитывая, что других комментариев или решений не было, я могу поэтому предположить, что нет стандартного способа обработки плохого XML-дизайна с помощью jaxb. Я все равно хотел бы найти лучшее решение. Благодарю. – Scottt