Java 技术和 XML 无疑是最近五年来最重要的编程开发工具。因此,用于在 Java 语言中处理 XML 的 API 就发展起来了。两个最流行的 —— 文档对象模型 (DOM) 和 Simple API for XML (SAX) —— 已经产生巨大的影响,JDOM 和数据绑定 API 也随之产生了(参阅 参考资料)。彻底理解其中一个或两个 API 是非常必要的;正确使用全部 API 会让您成为权威。但是,越来越多的 Java 开发人员发现他们不再需要广泛了解 SAX 和 DOM —— 这主要是由于 Sun Microsystems 的 JAXP 工具包。Java API for XML Processing (JAXP) 使得 XML 甚至对于 Java 初级开发人员也变得易于掌握,并大大提高了高级开发人员的能力。也就是说,即使使用 JAXP 的高级开发人员对于他们十分依赖的 API 也有误解。
本文假设您已基本了解 SAX 和 DOM。如果您完全不懂 XML 解析,那么可能需要首先阅读在线参考资料中有关 SAX 和 DOM 的信息,或者浏览我的书(参阅 参考资料)。您不需要精通回调或 DOM Node,但必须至少了解是 SAX 和 DOM 在解析 API。本文还有助于基本了解它们之间的差别。如果您掌握了这些基本知识,本文将对您更有帮助。
JAXP:是 API 还是抽象?
严格说来,JAXP 是 API,但更准确地说是抽象层。它没有提供解析 XML 的新方法,没有添
加到 SAX 或 DOM,也没有为 Java 和 XML 处理提供新功能。(如果您还不相信这一点,那么阅读这篇文章算对了。)但是,JAXP 使得使用 DOM 和 SAX 来处理一些困难任务变得更容易。它还允许以开发商中立的方式处理一些在使用 DOM 和 SAX API 时可能遇到的特定于开发商的任务。
逐渐晋级
在 Java 平台的早期版本中,JAXP 是核心平台中单独的下载。在 Java 5.0 中,JAXP 已经是 Java 语言的主要产品。如果已经有最新版本的 JDK(参阅 参考资料),您就已经获得了 JAXP。
没有 SAX、DOM 或另一个 XML 解析 API,则无法解析 XML。我曾经看到过许多关于将 SAX、DOM、JDOM 和 dom4j 与 JAXP 进行比较的请求,但作这样的比较是不可能的,因为前面四个 API 与 JAXP 具有完全不同的用途。SAX、DOM、JDOM 和 dom4j 都解析 XML。JAXP 提供了一种到达这些解析器及其所涉及的数据的方法,但并未提供一种解析 XML 文档的新方法。如果您要正确使用 JAXP,则理解此差别是非常必要的。这还很有可能使您远远领先于您的 XML 开发同行。
如果仍有疑问,请确保您具有 JAXP 发行版(参阅 逐渐晋级)。启动 Web 浏览器并加载 JAXP API 文档。导航至位于 l.parsers 软件包中的 API 的解析部分。令人奇怪的是,您将只到六个类。这个 API 到底怎么回事?所有这些类都位于现有解析器的顶部。其中两个类仅用于错误处理。JAXP 比人们想像的要简单得多。那么为何会有混淆呢?
位于顶部
甚至 JDOM 和 dom4j(参阅 参考资料)与 JAXP 一样都位于其他解析 API 的顶部。但这两个 API 都提供了从 SAX 或 DOM 中访问数据的不同模型,它们在内部使用 SAX(带有一些技巧和修改)来到达它们提供给用户的数据。
Sun 的 JAXP 和 Sun 的解析器
许多解析器/API 混淆来自于 Sun 软件包 JAXP 和该 JAXP 默认使用的解析器。在 JAXP 的早期版本中,Sun 包括 JAXP API(带有刚才提到的六个类和一些常用于转换的类) 一个叫做 Crimson 的解析器。Crimson 是 error parse newl 软件包的一部分。在 JAXP 的新版本中 —— 包括在 JDK 中 —— Sun 已经重新包装了 Apache Xerces 解析器(参阅 参考资料
。在这两种情况下,虽然解析器是 JAXP 发行版的一部分,但不是 JAXP API 的一部分。
可以认为是 JDOM 附带了 Apache Xerces 解析器。该解析器不是 JDOM 的一部分,但由 JDOM 使用,所以包括它是为了确保 JDOM 可以即装即用。同一原则适用于 JAXP,但并未明确公布:JAXP 附带解析器是为了可以立即使用。但是,许多人将 Sun 的解析器中包括的类作为 JAXP API 本身的一部分。例如,新闻组上的常见问题通常是“我如何使用 JAXP 附带的 XMLDocument 类?它的作用是什么?”答案有些复杂。
软件包名称中是什么?
当我第一次在 Java 1.5 中贸然打开源代码时,我惊奇于我所看到的 —— 或者更应该说是我没有 看到的。没有在正常中的软件包 s 中到 Xerces,因为 Sun 将 Xerces 类重新分配给了 s.internal。(我发现这有点不正常,但没有人问我。)在任何情况下,如果您在 JDK 中查 Xerces,就能到它。
首先,l.tree.XMLDocument 类不是 JAXP 的一部分。它是 Sun 的 Crimson 解析器的一部分,包装在 JAXP 的早期版本中。所以这个问题从一开始就令人误解。其次,J
AXP 的主要用途是在处理解析器时提供开发商独立性。有了 JAXP,您可以用 Sun 的 XML 解析器、Apache 的 Xerces XML 解析器和 Oracle 的 XML 解析器来处理相同的代码。因而使用特定于 Sun 的类会违反使用 JAXP 的要点。是否弄清楚了本主题是如何变得复杂起来的?JAXP 发行版中的 API 和解析器 已经组合在一起,一些开发人员误将解析器中的类和特性作为 API 的一部分,反之亦然。
既然弄清楚了所有的混淆,那么您就可以深入了解一些代码和概念了。
回页首
SAX 入门
SAX 是事件驱动的 XML 处理方法。它由许多回调组成。例如,startElement() 回调在每次 SAX 解析器遇到元素的起始标记时被调用。characters() 回调为字符数据所调用,然后 endElement() 为元素的结束标记所调用。许多回调用于文档处理、错误和其他词汇结构。您明白了。SAX 程序员实现一个 SAX 接口来定义这些回调。SAX 还提供一个叫做 DefaultHandler 的类(在 l.sax.helpers 软件包中)来实现所有这些回调,并提供所
有回调方法默认的空实现。(您将看到,这对于下一节 处理 DOM 中讨论 DOM 是重点。)SAX 开发人员只需要继承该类,然后实现需要插入特定逻辑的方法。所以 SAX 中的关键是提供这些各种回调的代码,然后让解析器在适当的时候触发其中的一个。下面是典型的 SAX 例程:
1. 使用特定开发商的解析器实现来创建 SAXParser 实例。
2. 注册回调实现(例如,通过使用继承 DefaultHandler 的类)。
3. 开始解析并在回调实现启动时停止。
JAXP 的 SAX 组件提供了完成所有这些操作的简单方法。没有 JAXP,SAX 解析器实例要么必须从开发商类(比如 s.parsers.SAXParser)中直接实例化,要么必须使用一个叫做 XMLReaderFactory 的 SAX 帮助类(也在 l.sax.helpers 软件包中)。第一种方法的问题很显然:它不是开发商中立的。第二种方法的问题在于,工厂需要使用解析器类的 String 名称作为参数(又是 Apache 类 s.parsers.SAXParser)。可以通过传递不同的解析器类作为 String 而更
改解析器。使用该方法,如果更改解析器名称,则不需要更改任何导入语句,但仍需要重新编译类。这显然不是最好的解决方案。如果能够不重新编译类而更改解析器就方便多了。
JAXP 提供了更好的备选方法:它允许将解析器作为 Java 系统特性。当然,从 Sun 中下载发行版时,您能得到使用 Sun 的 Xerces 版本的 JAXP 实现。更改解析器(比如更改为 Oracle 的解析器)需要更改类路径设置,从一个解析器实现移动到另一个解析器实现。但 需要重新编译代码。这就是 JAXP 的全部魔力 —— 抽象。
诡异的 SAX 开发人员
稍叉开一下话题。使用巧妙一点的编码,可以使得 SAX 应用程序从系统特性或特性文件中选择要使用的解析器类。但是,JAXP 提供了相同的行为,且无需任何工作,所以大多数人更愿意走 JAXP 路线。
SAX 解析器工厂一览
JAXP SAXParserFactory 类是能够轻易更改解析器实现的关键。必须创建该类的新实例(
一会将用到它)。新实例创建之后,工厂提供一种方法用于获得具有 SAX 功能的解析器。实际上,JAXP 实现保护着开发商相关的代码,从而使您的代码完全不受污染。工厂还具有一些其他的有用特性。
除了创建 SAX 解析器实例的基本工作之外,工厂还允许设置配置选项。这些选项影响通过工厂获得的所有解析器实例。JAXP 1.3 中两个常用的选项是,用于设置名称空间意识的 setNamespaceAware(boolean awareness) 和用于打开 DTD 验证的 setValidating(boolean validating)。记住,一旦设置了这些选项,它们将影响在方法调用后从工厂获得的所有实例。
设置了工厂之后,调用 newSAXParser() 会返回 JAXP SAXParser 类立即可用的实例。该类包装底层的 SAX 解析器(SAX 类 l.sax.XMLReader 的实例)。它还防止您使用解析器类的任何特定于开发商的附加项。(是否记得上文中有关 XmlDocument 类的 讨论?)该类允许启动实际的解析行为。清单 1 显示如何创建、配置和使用 SAX 工厂:

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。