java dom4j 解析xml_[Code]Java - dom / dom4j 解析XML文件遇到的几个问题

最近稍微接触了下用Java Dom 解析XML的文件。

遇到两个小问题,就在这里做个笔记吧~

1. Node 的 getNodeValue方法返回的一直是null。

其实还是由于对这个类不熟悉的关系,导致了这个问题。

Node有很多类型,一般 这种类型叫做Element Node。

需要得到其中的文本,直接使用getNodeValue方法是行不通的。

因为此Node中包含的文本其实是属于另外一种Node类型,即 Text Node。

所以此文本对应的Node,是上述 Element Node的子节点。

解决方法:如同网上各处所说的

.getFirstChild().getNodeValue(); (第一个子节点的Value值)

至于为啥Element Node的Node Value是null值,

参照JavaDoc可知,其定义就是如此。详细参照如下:

2. XML保存问题

使用了很多方法,不是有异常,就是输出为空文件。

后来发现,还是有一些需要注意的地方。

先上代码:

File f = new File( save_filename ); // 需要保存的名字

DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();

DocumentBuilder builder;

try {

builder = factory.newDocumentBuilder();

// createing a new DOM-document...

Document document = builder.newDocument(); // 1)

Element saveRoot = document.createElement("Root");

document.appendChild(saveRoot); // 2)

saveTree( saveRoot, document ); // 添加各种节点,建立DOM树

// Use a Transformer for output

TransformerFactory tFactory = TransformerFactory.newInstance();

Transformer transformer = tFactory.newTransformer();

transformer.setOutputProperty("indent", "yes"); // 3)

// transform DOM 2 XML file // 4)

DOMSource source = new DOMSource(document);

StreamResult result = new StreamResult( f );

transformer.transform(source, result);

} catch (ParserConfigurationException e) {

e.printStackTrace();

}

其中使用到的

DocumentBuilderFactory / DocumentBuilder /  TransformerFactory / DOMSource / StreamResult

意如其名,不用多解释了。

Question

1)全新 Document 的建立方式。

也可以使用读取时,建立的Document对象,只要更新相关的节点再保存即可。

此处为了练手,还是从头写了一遍。

2)document.appendChild 根节点

一开始词句忘记添加,所以导致输出空文本。

究其原因就是即使document.createElement后,也只是一个悬空节点,没有建立任何关系。

尤其是根节点,需要串联到document上。

3)此处即使使用了setOutputProperty("indent", "yes");

输出的文本文件,虽然节点之间有换行,

但是没有缩进,父节点和子节点的关系不是很明显。

解决方法:

在添加节点同时再添加一个上述的TextNode类型的子节点。

document.createTextNode("\n    ");

(不知道还有没有其他更加好的办法。。。)

4)DOMSource的建立和transformer的执行需要放在document树建立完毕以后。

一开始以为document更新以后,transform一下就好了。

而DOMSource只是存放了一个document的reference。

看来顺序还是很重要的。。。

[补充]

3. 节点 Atrribute 的顺序问题

使用dom的Node方法getAttributes()固然很方便。

NamedNodeMap attrs = node.getAttributes();

但是返回的类型NamedNodeMap按照Attribute的名字,按字典序排序了。

如果各个Attribute相互之间的顺序不能改变的情况下,此方法就不能适用了。

(不知道dom里面还有其他方法,使得得到的Attribute属性并不是按照字母排序的。望高手指点)

代替方案:

只能使用了dom4j的API读取XML了。

用后发现,比dom还要方便,非常简洁。

e.g. ReadXML

只要四句话

SAXReader reader = new SAXReader();

File file = new File(xmlFileName);

try {

this.doc = reader.read(file);// read xml file

} catch (DocumentException e) {

e.printStackTrace();

}

this.root = this.doc.getRootElement();  // get root

SAXReader reader = new SAXReader();

File file = new File(xmlFileName);

Document doc = reader.read(file);   // Get document

Element root = this.doc.getRootElement();  // get root

而Attribute的获取,也是按照固有xml的顺序,并没有按照字典序排序。

可使用Iterator遍历

for( Iterator It = element.attributeIterator(); It.hasNext(); ){

attribute =  It.next();

// do something

}

.over.

先暂时写这些吧。不足之处望高手指点~^_^

才疏学浅。。。初级问题,不足挂齿。。。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
要使用org.osgeo.proj4j库根据sumo可执行的net.xml中projParameter属性获取EPSG码,需要进行以下步骤: 1. 解析net.xml文件,获取projParameter属性值。 2. 使用proj4j库的ProjectionFactory类,根据projParameter属性值创建一个Projection对象。 3. 调用Projection对象的toWGS84()方法,将投影坐标系转换为WGS84坐标系。 4. 使用proj4j库的CRSRegistry类,根据toWGS84()方法返回的CRS对象获取EPSG码。 下面是一个示例代码: ```java import org.osgeo.proj4j.CRSFactory; import org.osgeo.proj4j.CRSRegistry; import org.osgeo.proj4j.CoordinateReferenceSystem; import org.osgeo.proj4j.ProjCoordinate; import org.osgeo.proj4j.Projection; import org.osgeo.proj4j.ProjectionException; import org.osgeo.proj4j.ProjectionFactory; import org.xml.sax.SAXException; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.parsers.ParserConfigurationException; import java.io.File; import java.io.IOException; public class NetXmlParser { public static void main(String[] args) { String netXmlFilePath = "path/to/net.xml"; String projParameter = getProjParameterFromNetXml(netXmlFilePath); int epsgCode = getEpsgCodeFromProjParameter(projParameter); System.out.println("EPSG code: " + epsgCode); } private static String getProjParameterFromNetXml(String netXmlFilePath) { String projParameter = null; try { DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); DocumentBuilder builder = factory.newDocumentBuilder(); org.w3c.dom.Document doc = builder.parse(new File(netXmlFilePath)); org.w3c.dom.Element root = doc.getDocumentElement(); projParameter = root.getAttribute("projParameter"); } catch (IOException | ParserConfigurationException | SAXException e) { e.printStackTrace(); } return projParameter; } private static int getEpsgCodeFromProjParameter(String projParameter) { CRSFactory crsFactory = new CRSFactory(); ProjectionFactory projectionFactory = new ProjectionFactory(); CoordinateReferenceSystem crs = crsFactory.createFromParameters("custom", projParameter); Projection projection = projectionFactory.createFromCoordinateSystems(crs, CRSRegistry.getCRS("EPSG:4326")); ProjCoordinate projCoord = new ProjCoordinate(0, 0); try { projection.transform(projCoord, projCoord); } catch (ProjectionException e) { e.printStackTrace(); } return CRSRegistry.lookupEpsgCode(crs, true); } } ``` 在上面的代码中,getProjParameterFromNetXml()方法解析了net.xml文件,并获取了projParameter属性值。getEpsgCodeFromProjParameter()方法使用projParameter属性值创建了一个Projection对象,并将其转换为WGS84坐标系。然后,该方法使用CRSRegistry类获取了CRS对象对应的EPSG码。最后,该方法返回EPSG码。 这样,我们就可以使用org.osgeo.proj4j库根据sumo可执行的net.xml中projParameter属性获取EPSG码了。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值