我试图从XML文件中读入一些数据,但遇到了一些问题,我的XML如下所示:
<Tree>
<child>
<Property Name="id"/>
<Property Name="username">abc</Property>
<Property Name="phoneType">phone1</Property>
<Property Name="value">123456</Property>
</child>
<child>
<Property Name="id"/>
<Property Name="username">def</Property>
<Property Name="phoneType">phone2</Property>
<Property Name="value">6789012</Property>
</child>
</Tree>
我试图将这些值作为字符串读入Java程序,到目前为止,我已经编写了以下代码:
File fXmlFile = new File("C:\\Users\\welcome\\Downloads\\ta\\abc.xml");
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
Document doc = dBuilder.parse(fXmlFile);
doc.getDocumentElement().normalize();
System.out.println("Root element :" + doc.getDocumentElement().getNodeName());
NodeList nList = doc.getElementsByTagName("child");
System.out.println("----------------------------");
for (int temp = 0; temp < nList.getLength(); temp++) {
Node nNode = nList.item(temp);
System.out.println("\nCurrent Element :" + nNode.getNodeName());
if (nNode.getNodeType() == Node.ELEMENT_NODE) {
Element eElement = (Element) nNode;
System.out.println("id id : "
+ eElement.getAttribute("id"));
我正在努力读取和打印id、用户名等的值。
无论如何,读取XML文件都不是一件小事。它要求读者对文件的结构有深入的了解。我的意思是,元素名称、属性名称、属性的数据类型、元素的顺序、元素是简单的还是复杂的(意味着它们是平面的还是下面有嵌套的元素)。
如Jon Skeet的评论所示,一种解决方案是使用Java文档API。此接口具有从XML文件获取数据所需的所有方法。然而,在我看来,这仍然给读者留下了知道元素和属性名称的任务。
如果给定XML的XML模式(XSD)或文档类型定义(DTD)可用或易于构造,我更喜欢使用许多库中的一个来解析XML内容;举几个例子:StaX、JDOM、DOM4j、JAXB。因为我已经广泛使用了它,所以我更喜欢JAXB。JAXB有一些限制,但这些限制超出了本文讨论的范围。值得一提的是,JAXB包含在Java6到10的Java发行版中。在这些版本之外,您必须自己下载JAXB发行版。
我使用JAXB的主要原因之一是,我可以使用POJO中的注释根据现有XML构造类,而无需构建模式。当然,这并不总是简单的。它几乎总是根据模式编译JAXB类。因为这将为XML文档生成Java自定义类,所以您可以通过元素的getter方法调用元素和属性,而不是让读者知道元素名称。
我使用OPs XML文件使用XML复制编辑器生成模式。结果架构如下所示:
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified">
<xs:element name="Tree">
<xs:complexType>
<xs:sequence>
<xs:element ref="child" maxOccurs="unbounded"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="child">
<xs:complexType>
<xs:sequence>
<xs:element ref="Property" maxOccurs="unbounded"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="Property">
<xs:complexType mixed="true">
<xs:attribute name="Name" type="xs:string" use="required"/>
</xs:complexType>
</xs:element>
</xs:schema>
一旦有了这个模式,就可以使用Java附带的XJC编译器来编译JAXB类。下面是一个关于如何编译JAXB类的示例:https://docs.oracle.com/javase/tutorial/jaxb/intro/examples.html
要下载JAXB编译器,请转到https://javaee.github.io/jaxb-v2/然后单击“下载独立发行版”。您可以将ZIP文件的内容放在计算机上的任何位置。然后,只需在您的环境变量上设置JAXB_HOME,就可以了。这似乎是一个很大的工作,但到目前为止,这些都是一次性的活动。好处是,当您设置好环境时,编译所有类需要几秒钟的时间;即使您需要基于XML生成模式。
执行编译器生成的树。java
,子级。java
和属性。java
。
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "", propOrder = {
"child"
})
@XmlRootElement(name = "Tree")
public class Tree {
@XmlElement(required = true)
protected List<Child> child;
public List<Child> getChild() {
if (child == null) {
child = new ArrayList<Child>();
}
return this.child;
}
}
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "", propOrder = {
"property"
})
@XmlRootElement(name = "child")
public class Child {
@XmlElement(name = "Property", required = true)
protected List<Property> property;
public List<Property> getProperty() {
if (property == null) {
property = new ArrayList<Property>();
}
return this.property;
}
}
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "", propOrder = {
"content"
})
@XmlRootElement(name = "Property")
public class Property {
@XmlValue
protected String content;
@XmlAttribute(name = "Name", required = true)
protected String name;
public String getContent() {
return content;
}
public void setContent(String value) {
this.content = value;
}
public String getName() {
return name;
}
public void setName(String value) {
this.name = value;
}
}
读取过程(解组)将XML文件转换为这些生成的数据类型。JAXB解组过程使用JAXBContext实用程序类创建解组器,然后调用散集方法将XML文件转换为对象:
JAXBContext context = JAXBContext.newInstance(Tree.class); // the argument is the root node
Tree xmlDoc = (Tree) context.createUnmarshaller().unmarshal(new FileReader("abc.xml")); // Reads the XML and returns a Java object
要编写,您将使用Java类存储数据并创建结构。在这种情况下,您需要创建所需的属性
对象、属性元素的子容器
以及作为树
节点的根节点。您可以一次添加一个元素,也可以创建元素列表,然后一次添加所有元素。填充根节点对象后,只需将其传递给封送拆收器。。。
JAXBContext context = JAXBContext.newInstance(Tree.class);
Marshaller mar= context.createMarshaller();
mar.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE); // formatting the xml file
mar.marshal(tree, new File("abc.xml")); // saves the "Tree" object as "abc.xml"
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.util.List;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBException;
import javax.xml.bind.Marshaller;
public class JAXBDemo {
public static void main(String[] args) {
try {
// write
Tree tree = new Tree();
Property prop0 = new Property();
prop0.setName("id");
prop0.setContent("");
Property prop1 = new Property();
prop1.setName("username");
prop1.setContent("abc");
Property prop2 = new Property();
prop2.setName("phoneType");
prop2.setContent("phone1");
Property prop3 = new Property();
prop3.setName("value");
prop3.setContent("123456");
List<Property> props1 = List.of(prop0, prop1, prop2, prop3);
Property prop4 = new Property();
prop4.setName("id");
prop4.setContent("");
Property prop5 = new Property();
prop5.setName("username");
prop5.setContent("def");
Property prop6 = new Property();
prop6.setName("phoneType");
prop6.setContent("phone2");
Property prop7 = new Property();
prop7.setName("value");
prop7.setContent("6789012");
List<Property> props2 = List.of(prop4, prop5, prop6, prop7);
Child child1 = new Child();
Child child2 = new Child();
child1.getProperty().addAll(props1);
child2.getProperty().addAll(props2);
tree.getChild().add(child1);
tree.getChild().add(child2);
JAXBContext context = JAXBContext.newInstance(Tree.class);
Marshaller mar= context.createMarshaller();
mar.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE);
mar.marshal(tree, new File("abc.xml"));
// read
Tree xmlDoc = (Tree) context.createUnmarshaller().unmarshal(new FileReader("abc.xml"));
List<Child> children = xmlDoc.getChild();
int i = 1;
for (Child child : children) {
System.out.println("Property " + i++ + ":");
List<Property> props = child.getProperty();
for (Property prop : props) {
System.out.println("Name: " + prop.getName() + "; Content: " + prop.getContent());
}
}
} catch (JAXBException | FileNotFoundException e) {
e.printStackTrace();
}
}
}
为了让它工作,我必须对发行版进行一些“修复”。第一个修复是编辑xjc。bat
根据这篇文章:https://github.com/eclipse-ee4j/jaxb-ri/issues/1321.滚动到底部以查看我应用的修复。
然后,我需要将我的“jaxb-runtime”依赖更新到版本2.3.3,以便项目能够与“jaxb-api”版本2.3.1一起工作。
可以使用XPath运行完全不同的查询。
File fXmlFile = new File("C:\\Users\\welcome\\Downloads\\ta\\abc.xml");
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
Document doc = dBuilder.parse(fXmlFile);
//Get an XPath object and evaluate the expression
XPath xpath = XPathFactory.newInstance().newXPath();
String propertyId = xpath.evaluate("/Tree/child[1]/Property[@name='id']", document);
更有可能的是,您希望循环遍历所有子元素,可以这样做
NodeList children = (NodeList)xpath.evaluate("/Tree/child", doc, XPathConstants.NODESET);
for (int i=0;i<children.getLength();i++) {
Element child = (Element)children.get(i);
String propertyId = child.getAttribute("id");
...
}
我建议您使用像jSoup这样的库来读取XML文件,因为您可以从盒子里得到很多功能。
另请阅读:如何使用jsoup解析XML
问题内容: 我需要使用Java读取XML文件。它的内容就像 是否有特殊的阅读器/ JAR,还是应该使用 FileInputStream进行 阅读? 问题答案: 另一个建议:尝试使用Commons消化器。这使您可以使用基于规则的方法非常快速地开发解析代码。有一个教程在这里和图书馆可在这里 我也同意Brian和Alzoid的观点,因为JAXB非常适合快速启动和运行。您可以使用JDK附带的xjc绑定编译
问题内容: EMF = Eclipse建模框架 我必须在一个课堂项目中使用EMF。我正在尝试了解如何使用EMF执行以下操作: 读取XML, 将值放入对象。 使用ORM将对象中的值持久保存到数据库中。-完成 使用ORM从数据库获取数据并生成XML。 我需要使用EMF(不知道是什么)和JPA(完成)来完成所有这些操作。 我使用过JAXB,我知道,可以使用JAXB完成,但是(EMF == JAXB)怎么
本文向大家介绍java如何解析/读取xml文件,包括了java如何解析/读取xml文件的使用技巧和注意事项,需要的朋友参考一下 本文实例为大家分享了java解析/读取xml文件的方法,供大家参考,具体内容如下 XML文件 Java 代码: 以上就是本文的全部内容,希望对大家的学习有所帮助。
问题内容: 我试图从XML文件中读取一些数据,但遇到麻烦,我拥有的XML如下: 我试图将这些值作为字符串读取到我的Java程序中,到目前为止,我已经编写了以下代码: 我正在努力读取实际的字符串值。 问题答案: 可能的实现之一: 与XML内容一起使用时: 结果并分配给上述和参考。
问题内容: 如何在Java中使用XPath读取XML? 问题答案: 你需要遵循以下要求: 然后,调用传入该代码中定义的文档和所需的返回类型,并将结果转换为结果的对象类型。 如果你需要有关特定XPath表达式的帮助,则可能应该将其作为单独的问题进行询问(除非首先是你的问题-我理解你的问题是如何在Java中使用API)。 此XPath表达式将为你提供下第一个URL元素的文本: 这将使你获得第二个:
问题内容: 我想使用Java中的XPath读取XML数据,因此对于我收集的信息,我无法根据需要解析XML。 这是我想做的: 通过其URL从联机获取XML文件,然后使用XPath对其进行解析,我想在其中创建两个方法。一种是输入特定的节点属性ID,然后得到所有的子节点,第二种是假设我只想获得一个特定的子节点值 在上面的示例中,如果我通过@name搜索,我想读取所有元素,并且我想只从@name’Java