<inputs>
<MAT_NO>123</MAT_NO>
<MAT_NO>323</MAT_NO>
<MAT_NO>4223</MAT_NO>
<FOO_BAR>122</FOO_BAR>
<FOO_BAR>125</FOO_BAR>
</inputs>
我必须解析上面的 XML。解析后,我希望这些值位于 Map<String, List<String>>
中与子节点对应的键值 - MAT_NO、FOO_BAR
和值 - 子节点的值 -123、323 等
以下是我的镜头。有没有更好的方法来做到这一点?
public class UserInputsXmlParser extends DefaultHandler {
private final SaveSubscriptionValues subscriptionValues = null;
private String nodeValue = "";
private final String inputKey = "";
private final List<String> valuesList = null;
private Map<String, List<String>> userInputs;
public Map<String, List<String>> parse(final String strXML) {
try {
final SAXParserFactory parserFactory = SAXParserFactory
.newInstance();
final SAXParser saxParser = parserFactory.newSAXParser();
saxParser.parse(new InputSource(new StringReader(strXML)), this);
return userInputs;
} catch (final SAXException e) {
e.printStackTrace();
throw new MyException("", e);
} catch (final IOException e) {
e.printStackTrace();
throw new MyException("", e);
} catch (final ParserConfigurationException e) {
e.printStackTrace();
throw new MyException("", e);
} catch (final Exception e) {
e.printStackTrace();
throw new MyException("", e);
}
}
@Override
public void startElement(final String uri, final String localName,
final String qName, final Attributes attributes)
throws SAXException {
nodeValue = "";
if ("inputs".equalsIgnoreCase(qName)) {
userInputs = MyUtil.getNewHashMap();
return;
}
}
@Override
public void characters(final char[] ch, final int start, final int length)
throws SAXException {
if (!MyUtil.isEmpty(nodeValue)) {
nodeValue += new String(ch, start, length);
} else {
nodeValue = new String(ch, start, length);
}
}
@Override
public void endElement(final String uri, final String localName,
final String qName) throws SAXException {
if (!"inputs".equalsIgnoreCase(qName)) {
storeUserInputs(qName, nodeValue);
}
}
/**
* @param qName
* @param nodeValue2
*/
private void storeUserInputs(final String qName, final String nodeValue2) {
if (nodeValue2 == null || nodeValue2.trim().equals("")) { return; }
final String trimmedValue = nodeValue2.trim();
final List<String> values = userInputs.get(qName);
if (values != null) {
values.add(trimmedValue);
} else {
final List<String> valueList = new ArrayList<String>();
valueList.add(trimmedValue);
userInputs.put(qName, valueList);
}
}
public static void main(final String[] args) {
final String sample = "<inputs>" + "<MAT_NO>154400-0000</MAT_NO>"
+ "<MAT_NO> </MAT_NO>" + "<MAT_NO>154400-0002</MAT_NO>"
+ "<PAT_NO>123</PAT_NO><PAT_NO>1111</PAT_NO></inputs>";
System.out.println(new UserInputsXmlParser().parse(sample));
}
}
更新: <inputs>
的 child 节点是动态的。我只知道根节点。
最佳答案
您是否必须提供解决方案作为 SAX 事件处理程序的一部分?如果没有,那么您可以使用周围众多 XML 库之一,例如 dom4j。使解决方案变得更加简单;
public static void main(String[] args) throws Exception
{
String sample = "<inputs>" + "<MAT_NO>154400-0000</MAT_NO>"
+ "<MAT_NO> </MAT_NO>" + "<MAT_NO>154400-0002</MAT_NO>"
+ "<PAT_NO>123</PAT_NO><PAT_NO>1111</PAT_NO></inputs>";
System.out.println(parse(sample));
}
static Map<String,List<String>> parse(String xml) throws Exception
{
Map<String,List<String>> map = new HashMap<String,List<String>>();
SAXReader reader = new SAXReader();
Document doc = reader.read(new StringReader(xml));
for (Iterator i = doc.getRootElement().elements().iterator(); i.hasNext();)
{
Element element = (Element)i.next();
//Maybe handle elements with only whitespace text content
List<String> list = map.get(element.getName());
if (list == null)
{
list = new ArrayList<String>();
map.put(element.getName(), list);
}
list.add(element.getText());
}
return map;
}
关于java - 解析 XML 并转换为集合,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3904270/