﻿<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>BlogJava-飞艳小屋-文章分类-XML</title><link>http://www.blogjava.net/songfei/category/5000.html</link><description>欢迎艳儿的加入</description><language>zh-cn</language><lastBuildDate>Tue, 27 Feb 2007 12:00:03 GMT</lastBuildDate><pubDate>Tue, 27 Feb 2007 12:00:03 GMT</pubDate><ttl>60</ttl><item><title>HTML操作XML数据岛，数据绑定 </title><link>http://www.blogjava.net/songfei/articles/66434.html</link><dc:creator>天外飞仙</dc:creator><author>天外飞仙</author><pubDate>Tue, 29 Aug 2006 06:31:00 GMT</pubDate><guid>http://www.blogjava.net/songfei/articles/66434.html</guid><wfw:comment>http://www.blogjava.net/songfei/comments/66434.html</wfw:comment><comments>http://www.blogjava.net/songfei/articles/66434.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/songfei/comments/commentRss/66434.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/songfei/services/trackbacks/66434.html</trackback:ping><description><![CDATA[１、XML的局限性 <br />目前，许多Web网站的内容数据都存放在数据库或数据文件中。对于Web程序开发人员来说，如果要想把有用的信息从数据库中提取出来，传统的方法是在服务器端编写脚本程序（如VBScript、JavaScript、CGI、ASP、Perl等等），通过对数据库执行SQL查询得到相关记录，然后把查询结果组织成HTML页面返回给客户端，用户使用浏览器观察最终结果。 <br />为了提高系统服务的灵活性、可扩展性，使服务对象范围更广，许多商业网站都尽可能地把商务规则、原始数据和表现形式当做相互独立的服务分别提供。HTML那种蕴数据于显示之中的方式显然不合乎这种需求。因此，把原始数据存放在XML文档中，使用样式单文件显示内容是XML技术适合于电子商务的优势所在。但从本质上来说，XSL技术不是面向数据显示的，它是一种格式转换技术，在显示手段和方式上都远不及HTML那样丰富。对编程人员来说，一种较为理想的方案是把HTML和XML两种技术相结合，优势互补，使真正的原始数据在能够保持本来意义和结构的同时，还能充分利用HTML那千变万化的显示技巧。XML数据岛就是这种技术融合的产物，它使用&lt;XML&gt;标签把XML数据直接嵌入到HTML页面中，从而实现了二者的优势互补。 <br /><br />２、IE中数据岛的处理方式 <br />为了能够处理这种内嵌XML代码的HTML页面，Internet Explorer 4.0（以下简称IE 4.0）引入了DSO（Data Source Objects，数据源对象）技术，用Java Applet实现。 <br />例如： <br />&lt;APPLET CODE=“com.ms.xml.dso.XMLDSO.class” ID=“xmldso” WIDTH=0 HEIGHT=0 MAYSCRIPT=TRUE&gt; <br />&lt;PARAM NAME=“URL” VALUE=“myXML.xml”&gt; <br />&lt;/APPLET&gt; <br />上述例子中，CODE属性指明了DSO Java小程序，MAYSCRIPT属性保证用户端脚本能够处理数据对象，PARAM标签指明了XML文档的位置。 <br />使用Java的局限性在于只能在HTML文档中说明XML的URL地址，而不能直接将XML标签嵌入其中，这就和真正的数据岛方案还有一定的差距。微软在Internet Explorer 5.0（以下简称IE 5.0）中对DSO技术进行了扩展，突破了以往的限制，使HTML和XML真正地融合到了一起。HTML页面中支持直接使用&lt;XML&gt;标签。 <br />例如： <br />&lt;HTML&gt; <br />&lt;XML ID=“xmldso”&gt; <br />&lt;?xml version=“1.0”?&gt; <br />some XML…… <br />&lt;/XML&gt; <br />只要保证每个数据岛的ID都是唯一的，就可以在页面中的任何必要的地方嵌入数据岛，并且这些DSO彼此都是相互独立的。 <br />除了上面例子中的这种直接嵌入方式，还可以使用外部引用方式链接数据岛。 <br />例如： <br />&lt;XML ID=“xmldso” SRC=“myXML.xml”&gt; <br />&lt;/XML&gt; <br />这样，只有当公司的客户对象继续使用IE 4.0，并且为了解决这部分客户的兼容性问题时，Java Applet才是编程人员要考虑的选择方案。 <br />在IE 5.0所实现的DSO技术中，如果数据是通过SQL语言对数据库进行查询得到的结果，那么就把它们存放在ADO（ActiveX Data Objects）记录集中。服务器把这种ActiveX控件（通常是ADO记录集）发送到客户端，由客户端脚本程序做进一步的处理。实际上，IE 5.0就是把XML数据岛作为一种特殊的ADO记录集进行处理的。 <br /><br />３、XML的数据绑定 <br />（1）ADO记录集的映射 <br />XML中的每一条主元素都被映射为ADO记录集中的一条记录，而子元素则相应地被映射到记录集中的字段（也称为域）。 <br />例如，存在XML数据岛books.xml如下： <br />&lt;XML ID=“xmldso”&gt; <br />&lt;?xml version=“1.0”?&gt; <br />&lt;booklist&gt; <br />&lt;book&gt; <br />&lt;title&gt;Straight Talk About Computers&lt;/title&gt; <br />&lt;isbn&gt;72-80088-005&lt;/isbn&gt; <br />&lt;/book&gt; <br />&lt;book&gt; <br />&lt;title&gt; Gourmet Microwave &lt;/title&gt; <br />&lt;isbn&gt;72-80081-082&lt;/isbn&gt; <br />&lt;/book&gt; <br />&lt;/booklist&gt; <br />&lt;/XML&gt; <br />此时，映射后的ADO记录集为： <br />title isbn <br />Straight Talk About Computers 72-80088-005 <br />Gourmet Microwave 72-80081-082 <br /> <br />（2）与HTML元素的绑定 <br /><br />在HTML文档中嵌入数据岛之后，就可以将XML数据岛与HTML元素绑定在一起。每一个DSO条目（即数据岛）都有唯一的ID号。首先将HTML元素中的DATASRC属性设置为相应的ID，就可以把HTML元素和数据岛联系在一起。然后再通过设置DATAFLD属性值，来确定所提取的XML元素。 <br /><br />例如，与DIV元素绑定的代码如下： <br />&lt;DIV ID=title DATASRC=#xmldso DATAFLD=“title”&gt;&lt;/DIV&gt; <br />&lt;DIV ID=price DATASRC=#xmldso DATAFLD=“isbn”&gt;&lt;/DIV&gt; <br />注意：并非所有的HTML元素都能与XML数据岛绑定。目前，支持这种DSO绑定机制的元素如下： <br />A、APPLET、BUTTON、DIV、FRAME、IFRAME、 IMG、INPUT (此处类型是：CHECKBOX、HIDDEN、 LABEL、PASSWORD、RADIO和TEXT)、LABEL、 MARQUEE、SELECT、SPAN、TABLE和 TEXTAREA。 <br /><br />（3）以表格方式显式XML数据 <br /><br />若把XML数据与TABLE元素绑定在一起，就可以自动地显示为多行的表格形式。 <br />例如，XML数据与TABLE元素绑定的代码如下： <br />&lt;TABLE BORDER=1 DATASRC=“#xmldso”&gt; <br />&lt;THEAD&gt; <br />&lt;TR&gt;&lt;TH&gt;Title&lt;/TH&gt; <br />&lt;TH&gt;ISBN&lt;/TH&gt;&lt;/TR&gt; <br />&lt;/THEAD&gt; <br />&lt;TBODY&gt; <br />&lt;TR&gt;&lt;TD&gt;&lt;DIV DATAFLD=“title”&gt;&lt;/DIV&gt;&lt;/TD&gt; <br />&lt;TD&gt;&lt;DIV DATAFLD=“isbn”&gt; <br />&lt;/DIV&gt;&lt;/TD&gt;&lt;/TR&gt; <br />&lt;/TBODY&gt; <br />&lt;/TABLE&gt; <br />这样，通过将TABLE元素中的DATASRC属性设定为#xmldso，把两者绑定起来。表格内部分为表头（THEAD）和表体（TBODY）两部分。每一个&lt;book&gt;元素都会显示为一行表格，具体每一栏显示哪一项数据，则由DIV元素中的DATAFLD属性指定。 <br /><br /><br />１、XML的嵌套处理 <br />一般情况下，我们从数据库中查询得到的结果集可能很大，所以从服务器返回到客户端时，数据会被分成若干个页面分别进行传递。此时，<strong>利用TABLE元素中的DATAPAGESIZE属性可以指定每个页面包含记录集条目的个数。 <br /></strong>例如： <br />&lt;TABLE DATASRC=“#xmldso” DATAPAGESIZE=10&gt; <br />很显然，如果XML数据格式是对称的，则无论是映射到ADO记录集还是绑定到表格元素上，效果都会很好。而在实际应用中，XML数据为非对称的例子也很多，比如一本书的作者可能就不止一位，这在映射和绑定时都会产生一定的麻烦。解决问题的办法就是利用嵌套。每一行表格仍对应一条主元素，每一栏也对应着一个子元素。对于重复元素，则使用嵌套的表格。我们假设在books.xml中，第一本书的作者为Dean Straight，第二本书的作者为Charlotte Cooper、Shelley Burke和Regina Murphy。此时，绑定过程如下： <br />● 创建TABLE元素，并将数据岛ID赋值给DATAFLD属性； <br />● 对于单独的XML元素，如&lt;isbn&gt;，创建TD元素，并设定相应的DATAFLD属性； <br />● 对于重复元素，在TD元素内部嵌套一个表格； <br />● 用单行单列的形式显示作者信息。 <br />注意这里的DATAFLD属性必须设定为“$TEXT”， <br />以保证嵌套元素的内容被全部显示在指定的元素中。 <br />完整的HTML代码如下所示： <br />&lt;TABLE BORDER=1 DATASRC=“#xmldso”&gt; <br />&lt;THEAD&gt;&lt;TR&gt;&lt;TH&gt;Title&lt;/TH&gt; <br />&lt;TH&gt;ISBN&lt;/TH&gt; <br />&lt;TH&gt;Author&lt;/TH&gt;&lt;/TR&gt;&lt;/THEAD&gt; <br />&lt;TBODY&gt; <br />&lt;TR&gt;&lt;TD&gt; <br />&lt;DIV DATAFLD=“title”&gt;&lt;/DIV&gt;&lt;/TD&gt; <br />&lt;TD&gt;&lt;DIV DATAFLD=“isbn”&gt; <br />&lt;/DIV&gt;&lt;/TD&gt; <br />&lt;TD&gt; <br />&lt;TABLE BORDER=0 DATASRC=“#xmldso” DATAFLD=“author”&gt; <br />&lt;TR&gt;&lt;TD&gt;&lt;SPAN DATAFLD=“$Text”&gt;&lt;/SPAN&gt;&lt;/TD&gt;&lt;/TR&gt; <br />&lt;/TABLE&gt; <br />&lt;/TD&gt; <br />&lt;/TR&gt;&lt;/TBODY&gt; <br />&lt;/TABLE&gt; <br />事实上，使用DSO效果最好的情况是针对结构对称的数据，而处理非对称数据更有效的办法是使用我们以后将要介绍的DOM技术。 <br />２、DSO技术的应用 <br />1．访问元素的属性 <br />用DSO访问元素的属性很简单，可以直接把属性按子元素来处理。 <br />例如： <br />&lt;book isbn=“9-001-122-12”&gt; <br />…… <br />&lt;/book&gt; <br />这样，在绑定到HTML表格中时，就可以直接按子元素来处理： <br />&lt;TD&gt;&lt;SPAN DATAFLD=“isbn”&gt; &lt;/SPAN&gt;&lt;/TD&gt; <br />如果遇到属性名和子元素名一样的情况，在元素名前加上“!”进行区分。 <br /><br />2．遍历记录集 <br /><font color="#006400">DSO把XML数据岛当做ADO记录集进行处理的一大好处是可以利用ADO提供的各种方法对数据源进行访问，<strong><u>尤其是当把数据岛与类似SPAN、DIV和INPUT等HTML元素绑定时。通常这些元素显示的是记录集的首条记录</u>，</strong>要想对记录集进行遍历浏览，可以使用ADO的方法 : Move、MoveFirst、MoveLast、MoveNext和MovePrevious。比如创建一个按钮响应函数，只要用户点击“Next”按钮，就可以逐条浏览相应的记录。</font> <br />例如： <br />&lt;XML ID=“xmldso” SRC=“books.xml”&gt; <br />&lt;/XML&gt; <br />Sub btnNext_onclick() <br />xmldso.RecordSet.MoveNext <br />End Sub <br /><br />3．与Script语言相结合 <br />有些用户比较习惯编写Script语言，利用DSO技术同样可以与各种Script很好地结合在一起。 <br />例如（以VB Script为例），访问记录集时，代码如下:  <br />Dim rsBooks <br />Set rsBooks = xmldso.RecordSet <br />访问字段（子元素）的值： <br />Dim sTitle <br />sTitle = rsBooks(“title”) <br />可以使用innerText和innerHTML属性把得到的值传递给HTML元素。例如，有一个DIV元素名为divTitle，赋值代码如下所示： <br />divTitle.innerTEXT = sTitle <br />利用脚本程序还可以处理许多DSO事件，下表列举了其中的一部分事件： <br />事件 触发事件 响应 <br />onDataAvailable 新数据准备就绪 当前运行状态中记录集中条目的个数 <br />onDataSetComplete 数据源中的所有数据已经到达 显示数据，或返回一个确认消息 <br />onDataSetChanged 记录集中的数据修改完毕，可以访问 显示更新后的数据 <br />onRowEnter 当前记录指针已经移动 在显示数据前对数据进行必要的格式化 <br /> <br />在脚本中处理各种事件的方法就是在&lt;SCRIPT&gt;标签中使用FOR属性指定XML数据岛ID，使用EVENT属性确定事件类型。 <br />例如，获取记录集中条目的个数： <br />&lt;SCRIPT Language=“VB Script” FOR=“xmldso” EVENT=“onDataAvailable”&gt; <br />lblRecords.value = booklist.RecordSet.RecordCount <br />&lt;/SCRIPT&gt; <br />除了显示记录数据之外，脚本程序还可以对记录集进行快速查询、排序、编辑等操作。但要指出的是，虽然ADO技术中提供了类似SortColumn和SortAscending等方法对XML数据进行排序，但是效果不如XSL中的排序操作，所以建议大家充分利用XSL技术来实现这部分功能。 <br />其余的功能，如利用脚本对记录集进行诸如增加、删除、修改等操作，或是分页显示HTML表格等等，在这里就不一一举例说明了，用法与前面的操作大同小异。最后需要说明的是，所有对DSO对象的操作都是在用户端完成的，实际上是服务器数据对象的一份复制品，这样做的好处是避免了网络承受大量数据通信的负担。但这时用户端所做的任何操作对服务器上存储的数据毫无影响，如果要想对服务器记录也进行修改，那么就要用到客户端与服务器端的数据交换技术，我们将在以后对此进行介绍。  <img src ="http://www.blogjava.net/songfei/aggbug/66434.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/songfei/" target="_blank">天外飞仙</a> 2006-08-29 14:31 <a href="http://www.blogjava.net/songfei/articles/66434.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>XML配置文件的读取(sax)</title><link>http://www.blogjava.net/songfei/articles/63903.html</link><dc:creator>天外飞仙</dc:creator><author>天外飞仙</author><pubDate>Wed, 16 Aug 2006 06:51:00 GMT</pubDate><guid>http://www.blogjava.net/songfei/articles/63903.html</guid><wfw:comment>http://www.blogjava.net/songfei/comments/63903.html</wfw:comment><comments>http://www.blogjava.net/songfei/articles/63903.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/songfei/comments/commentRss/63903.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/songfei/services/trackbacks/63903.html</trackback:ping><description><![CDATA[
		<h2 id="pageName">XML配置文件的读取(sax)<br /><span style="FONT-SIZE: 12px; COLOR: #cccccc">JSP教程-Java与XML</span></h2>
		<div class="story">
				<span style="FLOAT: right; TEXT-ALIGN: center">
						<script type="text/javascript">
								<!--
google_ad_client = "pub-1294368471619564";
google_ad_width = 250;
google_ad_height = 250;
google_ad_format = "250x250_as";
google_ad_type = "text";
google_ad_channel ="";
google_color_border = "B4D0DC";
google_color_bg = "ECF8FF";
google_color_link = "0000CC";
google_color_url = "008000";
google_color_text = "6F6F6F";
//-->
						</script>
						<script src="http://pagead2.googlesyndication.com/pagead/show_ads.js" type="text/javascript">
						</script>
						<script language="VBScript"><![CDATA[
 on error resume next 
 dim plugins,names,backward_compatibility_index,comp_flags  
plugins = Array("acroPDF.PDF.1", "PDF.PdfCtrl.6", "PDF.PdfCtrl.5","PDF.PdfCtrl.4", "ShockwaveFlash.ShockwaveFlash.7","ShockwaveFlash.ShockwaveFlash.6", "ShockwaveFlash.ShockwaveFlash.5","ShockwaveFlash.ShockwaveFlash.4", "QuickTime.QuickTime.4","QuickTimeCheckObject.QuickTimeCheck.1","rmocx.RealPlayer G2 Control.1","SWCt1.SWCt1.9", "SWCt1.SWCt1.8", "SWCt1.SWCt1.7", "SWCt1.SWCt1.1","MediaPlayer.MediaPlayer.1", "Adobe.SVGCtl") 
 names = Array("ar7", "ar6", "ar5", "ar4", "f7", "f6", "f5", "f4", "q4", "qp", "rp", "sw9", "sw8", "sw7", "swp", "wmp", "svg") 
backward_compatibility_index = Array(1, 1, 1, 1, 2, 2, 2, 2, 0, 0, 0, 3, 3, 3, 3, 0, 0) 
comp_flags = Array(0, 0, 0, 0) 
for i = 0 to UBound(names) 
  result = False 
  result = IsObject(CreateObject(plugins(i))) 
  flag_index = backward_compatibility_index(i) 
  if (result and comp_flags(flag_index) = 0) Then 
    pluginlist = pluginlist & names(i) & "," 
    if(flag_index > 0)  Then comp_flags(flag_index) = 1 
  end If 
next 
]]&gt;</script>
				</span>
				<span id="ArticleContent1_ArticleContent1_lblContent">  
<p>在最近的一个MIS项目中,为了避免硬编码,我需要把一些配置信息写在一个配置文件中.考虑到是J2EE项目,J2EE的配置文件<br />好像都是xml文件了,再用传统ini文件是不是有点落伍了?<br />ok,就用xml做配置文件吧.<br />我的配置文件reportenv.xml如下,比较简单:</p><p>&lt;?xml version="1.0" encoding="utf-8"?&gt;<br />&lt;reportenv&gt;<br />&lt;datasource&gt;<br />&lt;username&gt;sqlname&lt;/username&gt;<br />&lt;password&gt;password&lt;/password&gt;<br />&lt;/datasource&gt;<br />&lt;/reportenv&gt;</p><p>现在的问题是我用什么来读取配置信息?<br />现在流行的是dom4j和sax,我以前一直用dom4j.可是weblogic workshop自带的是sax,我又不想再引入包了,于是就是sax吧.<br />第一步:ConfigParser.java<br />/*<br /> * Create Date: 2005-6-13 <br /> * Create By: 板桥里人<br /> * purpose:xml配置文件属性读取器<br /> */<br />package com.infoearth.report; </p><p>import org.xml.sax.Attributes;<br />import org.xml.sax.helpers.DefaultHandler;<br />import org.xml.sax.SAXException; <br />import java.util.Properties;</p><p>public class ConfigParser extends DefaultHandler {</p><p>    ////定义一个Properties 用来存放属性值<br />    private Properties props;</p><p>    private String currentSet;<br />    private String currentName;<br />    private StringBuffer currentValue = new StringBuffer();</p><p>    //构建器初始化props<br />    public ConfigParser() {</p><p>        this.props = new Properties();<br />        }</p><p>    public Properties getProps() {<br />        return this.props;<br />        }</p><p>    //定义开始解析元素的方法. 这里是将&lt;xxx&gt;中的名称xxx提取出来.<br />    public void startElement(String uri, String localName, String qName, Attributes attributes) <br />    throws SAXException {<br />        currentValue.delete(0, currentValue.length());<br />        this.currentName =qName;<br />        }</p><p>    //这里是将&lt;xxx&gt;&lt;/xxx&gt;之间的值加入到currentValue<br />    public void characters(char[] ch, int start, int length) throws SAXException { <br />        currentValue.append(ch, start, length);<br />        }</p><p>    //在遇到&lt;/xxx&gt;结束后,将之前的名称和值一一对应保存在props中<br />    public void endElement(String uri, String localName, String qName) throws SAXException {<br />        props.put(qName.toLowerCase(), currentValue.toString().trim());<br />        }</p><p>    }<br />    <br /> 第二步:ParseXML.java<br /> /*<br /> * Create Date: 2005-6-13 <br /> * Create By: 板桥里人 李春雷修改<br /> * purpose:xml配置文件属性读取器(通用),<br /> */<br /> <br />package com.infoearth.report; </p><p>import java.util.Properties;<br />import javax.xml.parsers.SAXParser;<br />import javax.xml.parsers.SAXParserFactory;<br />import java.net.URL;</p><p>public class ParseXML{<br />    //定义一个Properties 用来存放属性值<br />    private Properties props;</p><p>    public Properties getProps() {<br />        return this.props;<br />        }</p><p>    public void parse(String filename) throws Exception {<br />        //将我们的解析器对象化<br />        ConfigParser handler = new ConfigParser();<br />        //获取SAX工厂对象<br />        SAXParserFactory factory = SAXParserFactory.newInstance();<br />        factory.setNamespaceAware(false);<br />        factory.setValidating(false);<br />        //获取SAX解析<br />        SAXParser parser = factory.newSAXParser();<br />        try{<br />            //将解析器和解析对象xml联系起来,开始解析 <br />            parser.parse(filename, handler);<br />            //获取解析成功后的属性<br />            props = handler.getProps();<br />            }finally{<br />                factory=null;<br />                parser=null;<br />                handler=null;<br />                }<br />        }<br />    }<br />第三步:ReadConfigXml.java<br />/*<br /> * Create Date: 2005-6-13 <br /> * Create By: 李春雷<br /> * purpose:xml配置文件属性读取器<br /> */</p><p>package com.infoearth.report; </p><p>import java.util.Properties;</p><p>public class ReadConfigXml <br />{<br />    private Properties props;<br />    <br />    public ReadConfigXml(String url){<br />  ParseXML myRead = new ParseXML();<br />   try {<br />    myRead.parse(url);<br />                props = new  Properties(); <br />                props = myRead.getProps();<br />   } catch (Exception e) {<br />    e.printStackTrace();<br />   }      <br />        }<br />   public  String getUserName(){<br />        return props.getProperty("username");<br />        }        <br />   public String getPassWord(){<br />        return props.getProperty("password");<br />    }</p><p>} </p><p><br />ok,搞定了,读取的时候如下:<br />ReadConfigXml xmlread = new ReadConfigXml("reportenv.xml");<br />String username = xmlread.getUserName();<br />String password = xmlread.getPassWord();</p><p>前两个类实现了xml文档属性设置的任意读取.只要是xml的属性值,都读到了property中,你只需在property中提取就可以了.<br />第三个类是我针对我的xml文件写的,似乎有点多余.呵呵.其实有难言之隐.因为不想过多的改动以前的程序架构,就画蛇添<br />足了一下.</p><p>另外,感谢j道,感谢板桥里人.</p><p></p></span>
		</div>
<img src ="http://www.blogjava.net/songfei/aggbug/63903.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/songfei/" target="_blank">天外飞仙</a> 2006-08-16 14:51 <a href="http://www.blogjava.net/songfei/articles/63903.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>java操作xml编程实例(sax)</title><link>http://www.blogjava.net/songfei/articles/63882.html</link><dc:creator>天外飞仙</dc:creator><author>天外飞仙</author><pubDate>Wed, 16 Aug 2006 05:29:00 GMT</pubDate><guid>http://www.blogjava.net/songfei/articles/63882.html</guid><wfw:comment>http://www.blogjava.net/songfei/comments/63882.html</wfw:comment><comments>http://www.blogjava.net/songfei/articles/63882.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/songfei/comments/commentRss/63882.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/songfei/services/trackbacks/63882.html</trackback:ping><description><![CDATA[
		<p>XML文档样本： </p>
		<p>
				<br />&lt;?xml version="1.0"?&gt; <br />&lt;simple date="7/7/2000" &gt; <br />&lt;name&gt; Bob &lt;/name&gt; <br />&lt;location&gt; New York &lt;/location&gt; <br />&lt;/simple&gt; </p>
		<p>
				<br />代码: <br />package xmltest; <br />import javax.xml.parsers.*; <br />import org.xml.sax.*; <br />import org.xml.sax.helpers.*; <br />import java.io.*; </p>
		<p> </p>
		<p>
				<br />public class SaxTest extends DefaultHandler { </p>
		<p>
				<br />// 重载DefaultHandler类的方法 <br />// 以拦截SAX事件通知。 <br />// <br />// 关于所有有效事件，见org.xml.sax.ContentHandler <br />// <br />public void startDocument( ) throws SAXException { <br />System.out.println( "SAX Event: START DOCUMENT" ); <br />} </p>
		<p>public void endDocument( ) throws SAXException { <br />System.out.println( "SAX Event: END DOCUMENT" ); <br />} </p>
		<p>public void startElement( String namespaceURI, <br />String localName, <br />String qName, <br />Attributes attr ) throws SAXException { <br />System.out.println( "SAX Event: START ELEMENT[ " + <br />localName + " ]" ); </p>
		<p>// 如果有属性，我们也一并打印出来．．． <br />for ( int i = 0; i &lt; attr.getLength(); i++ ){ <br />System.out.println( " ATTRIBUTE: " + <br />attr.getLocalName(i) + <br />" VALUE: " + <br />attr.getValue(i) ); <br />} </p>
		<p>} </p>
		<p>public void endElement( String namespaceURI, <br />String localName, <br />String qName ) throws SAXException { <br />System.out.println( "SAX Event: END ELEMENT[ " + <br />localName + " ]" ); <br />} </p>
		<p>public void characters( char[] ch, int start, int length ) <br />throws SAXException { </p>
		<p>System.out.print( "SAX Event: CHARACTERS[ " ); </p>
		<p>try { <br />OutputStreamWriter outw = new OutputStreamWriter(System.out); <br />outw.write( ch, start,length ); <br />outw.flush(); <br />} catch (Exception e) { <br />e.printStackTrace(); <br />} </p>
		<p>System.out.println( " )" ); </p>
		<p>} </p>
		<p>
				<br />public static void main( String[] argv ){ </p>
		<p>System.out.println( "Example1 SAX Events:" ); <br />try { </p>
		<p>// SAXParserFactory spFactory = SAXParserFactory.newInstance(); <br />// SAXParser sParser = spFactory.newSAXParser(); </p>
		<p>
				<br />// 建立SAX 2解析器．．． <br />XMLReader xr = XMLReaderFactory.createXMLReader("org.apache.xerces.parsers.SAXParser"); </p>
		<p>// 安装ContentHandler．．． <br />xr.setContentHandler( new SaxTest() ); </p>
		<p>// 解析文件．．． <br />xr.parse( new InputSource( <br />new FileReader( "exampleA.xml" )) ); </p>
		<p>
				<br />}catch ( Exception e ) { <br />e.printStackTrace(); <br />} </p>
		<p>} </p>
		<p>} <br /> 当前SAX API有两个版本。第二版中的类名和方法名与第一版都有出入，但是代码的结构是一样的。<br />    SAX是一套API，它不是一个解析器，所以这个代码在XML解析器中是通用的。要让示例跑起来，你将需要一个支持SAX v2的XML解析器。我用Apache的Xerces解析器.代码如下<br />// 建立SAX 2解析器．．． <br />XMLReader xr = XMLReaderFactory.createXMLReader("org.apache.xerces.parsers.SAXParser"); </p>
		<p>// 安装ContentHandler．．． <br />xr.setContentHandler( new SaxTest() ); <br />SAX API 的说明书通俗易读。它包含了很多的详细内容。而使用SAX API的主要任务就是创建一个实现ContentHandler接口，一个供XML 解析器调用以将分析XML文档时所发生的SAX事件分发给处理程序的回调接口。 </p>
		<p>方便起见，SAX API也提供了一个已经实现了ContentHandler接口的DefaultHandler适配器类。 </p>
		<p>一但实现了ContentHandler或者扩展了DefaultHandler类，你只需直接将XML解析器解析一个特定的文档即可。 </p>
		<p>我们的第一个例子扩展DefaultHandler将每个SAX事件打印到控制台。这将给你一个初步的映象，以说明什么SAX事件将会发生及以怎样的顺序发生。 <br /></p>
<img src ="http://www.blogjava.net/songfei/aggbug/63882.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/songfei/" target="_blank">天外飞仙</a> 2006-08-16 13:29 <a href="http://www.blogjava.net/songfei/articles/63882.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>浅谈stax</title><link>http://www.blogjava.net/songfei/articles/53294.html</link><dc:creator>天外飞仙</dc:creator><author>天外飞仙</author><pubDate>Fri, 16 Jun 2006 06:21:00 GMT</pubDate><guid>http://www.blogjava.net/songfei/articles/53294.html</guid><wfw:comment>http://www.blogjava.net/songfei/comments/53294.html</wfw:comment><comments>http://www.blogjava.net/songfei/articles/53294.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/songfei/comments/commentRss/53294.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/songfei/services/trackbacks/53294.html</trackback:ping><description><![CDATA[
		<span id="LblContent">
				<span id="LblContent">stax(simple stream api for xml)作为jsr已经出现几年时间了，可能不如sax,dom(及其他基于其上的工具包比如jdom,jaxp,etc)为众人所知。可能也是因为最近xfire的火热 导致它的知名度有所提升吧。（题 外话，好象有不少知识点一直都是默默无闻的，只有随着某项技术的流行才突然变的为人所知道了，比如ThreadLocal本来我们一直没有接触，很多人可能一直都不知道它的存在，但随着它在spring ,hibernate这些流行的技术里的灵巧的应用，一下子就被很多人谈及及应用了。可见我们的水平还是属于跟在老外屁股后面跑的水平）。<br />通过和dom,sax这两种大家熟知的xml解析方式的比较，可以容易的看出它的特点。<br />dom通过把整个tree 文档读入内存进行操作，可以随意对文档进行操作，非常灵活。但缺点是对内存的资源耗费比较大。<br />sax不同于dom把整个文档读入内存的方式，它是直接对 xml文件进行操作。速度快，基本上不占用什么内存资源。缺点看看它的名字就知道了(simple api for xml),基于event的方式（这点和stax类似），但是是通过callback的方式把对xml的遍历权交给sax parser了。这样导致我们不能灵活控制对xml文件的访问。<br /><br />stax通过stream的方式来解决sax,dom各自的缺点，同时具有他们大部分的优点（我想底层实现是不是通过直接操作文件流的方式，还没有看它的实现的src，不敢乱说）。stax主要有两中粒度不同的操作方式 ，一种基于event, 另一种更底层的实现基于cursor。初一看实现方式有点象sax,因为都是基于event的。但是sax把访问控制权交给parser(通过callback))了，我们很难控制iterat过程。stax允许我们自己控制iterat.<br />所以stax的优点如下：基于stream的方式，不象dom耗费内存资源。又可以自己控制对xml的iterat，不象sax把控制权交给parser).还有一个优点就是可以在iterat的过程中随时cancel。虽然sax 也可以通过 throw saxexception的方式中断iterat过程，但毕竟不是一中优美的解决方案。当然stax的还提供了以stream的方式进行write xml的操作。<br /><br />?具体的stax应用可以看ibm的系列教程文章，比较老了了点。http://www-128.ibm.com/developerworks/xml/library/x-tipstx/<br /><br />具体实现，除了bea的一个ri实现外，不知道还有其他的实现没有（stax jsr好象最早由bea提出来）？<br /><br />个人感觉stax的应用还是有些麻烦，期待（或则是不是已经有了？）能有更高层次的封装（类似于jdom,jaxp实现之类的）。<br /><br /></span>
		</span>
<img src ="http://www.blogjava.net/songfei/aggbug/53294.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/songfei/" target="_blank">天外飞仙</a> 2006-06-16 14:21 <a href="http://www.blogjava.net/songfei/articles/53294.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>java操作XML</title><link>http://www.blogjava.net/songfei/articles/36346.html</link><dc:creator>天外飞仙</dc:creator><author>天外飞仙</author><pubDate>Mon, 20 Mar 2006 07:57:00 GMT</pubDate><guid>http://www.blogjava.net/songfei/articles/36346.html</guid><wfw:comment>http://www.blogjava.net/songfei/comments/36346.html</wfw:comment><comments>http://www.blogjava.net/songfei/articles/36346.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/songfei/comments/commentRss/36346.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/songfei/services/trackbacks/36346.html</trackback:ping><description><![CDATA[
		<p>package jp.co.nec.ome.utility.xml;</p>
		<p>import java.io.*;<br />import javax.xml.parsers.*;</p>
		<p>import org.w3c.dom.*;<br />import org.xml.sax.*;</p>
		<p>//*****************************************************************************<br />/**<br /> * XML文書分析クラスです。&lt;BR&gt;<br /> * XMLに記述されている定義を分析し、子要素や子要素の内容の取扱を容易にする<br /> * ユーティリティクラスです。<br /> * &lt;P&gt;<br /> * @author  Hisaya Saito<br /> * @version $Revision:   5.2  $ $Date:   20 May 2005 10:24:55  $<br /> * @since   OpenMeisterEnterprise/EF 3.2<br /> */<br />//*****************************************************************************<br />public class OmXMLAnalyzer {</p>
		<p>  //***************************************************************************<br />  //コンストラクタ<br />  //***************************************************************************</p>
		<p>  //***************************************************************************<br />  /**<br />   * privateのコンストラクタです。&lt;BR&gt;<br />   * スタティックメソッドのみの利用とし、インスタンス化は不許可とします。<br />   */<br />  //***************************************************************************<br />  private OmXMLAnalyzer() {<br />  }</p>
		<p>  //***************************************************************************<br />  //publicメソッド<br />  //***************************************************************************</p>
		<p>  //***************************************************************************<br />  /**<br />   * XMLファイルパスの文字列からXML文書のルート要素を取得します。<br />   * @param  argFilePath XMLファイルパス<br />   * @return ルート要素<br />   * @exception FileNotFoundException 何らかの理由でファイルを開くことができない場合<br />   * @exception ParserConfigurationException 要求された構成を満たすDocumentBuilderを生成できない場合<br />   * @exception SAXException 構文解析エラーが発生した場合<br />   * @exception IOException 入出力エラーが発生した場合<br />   */<br />  //***************************************************************************<br />  public static Element getRootElement(String argFilePath)<br />                                           throws FileNotFoundException,<br />                                                  ParserConfigurationException,<br />                                                  SAXException,<br />                                                  IOException {</p>
		<p>    Element rootElement = null;</p>
		<p>    //XML文書解釈のためのParserの作成<br />    File defineFile = new File(argFilePath);<br />    InputStream inputStream = new FileInputStream(defineFile);<br />    try {<br />      DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();<br />      DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();<br />      Document document = documentBuilder.parse(inputStream);</p>
		<p>      //XML文書のツリーの最上位の要素rootを取得します。<br />      rootElement = document.getDocumentElement();<br />    } finally {<br />      inputStream.close();<br />    }<br />    return rootElement;<br />  }</p>
		<p>  //***************************************************************************<br />  /**<br />   * 入力ストリームからXML文書のルート要素を取得します。<br />   * @param  argInputStream<br />   * @return ルート要素<br />   * @exception FileNotFoundException 何らかの理由でファイルを開くことができない場合<br />   * @exception ParserConfigurationException 要求された構成を満たすDocumentBuilderを生成できない場合<br />   * @exception SAXException 構文解析エラーが発生した場合<br />   * @exception IOException 入出力エラーが発生した場合<br />   */<br />  //***************************************************************************<br />  public static Element getRootElement(InputStream argInputStream)<br />      throws FileNotFoundException,<br />             ParserConfigurationException,<br />             SAXException,<br />             IOException {</p>
		<p>    Element rootElement = null;</p>
		<p>    //XML文書解釈のためのParserの作成<br />    try {<br />      DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();<br />      DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();<br />      Document document = documentBuilder.parse(argInputStream);</p>
		<p>      //XML文書のツリーの最上位の要素rootを取得します。<br />      rootElement = document.getDocumentElement();<br />    } finally {<br />      argInputStream.close();<br />    }<br />    return rootElement;<br />  }</p>
		<p>  //***************************************************************************<br />  /**<br />   * 指定した親要素の中で最初の子要素を取得します。<br />   * @param  argParentElement    親要素<br />   * @param  argChildElementName 子要素名<br />   * @return 最初に取得できた子要素<br />   */<br />  //***************************************************************************<br />  public static Element getChildElement(Element argParentElement,<br />                                        String argChildElementName) {<br />    return getChildElement(argParentElement, argChildElementName, 0);<br />  }</p>
		<p>  //***************************************************************************<br />  /**<br />   * 指定した親要素の中の指定した順番の子要素を取得します。<br />   * @param  argParentElement       親要素<br />   * @param  argChildElementName         子要素名<br />   * @param  argSpecificationNumber 順番<br />   * @return 指定した順番の子要素<br />   */<br />  //***************************************************************************<br />  public static Element getChildElement(Element argParentElement,<br />                                        String argChildElementName,<br />                                        int argSpecificationNumber) {<br />    NodeList childNodeList =<br />                    argParentElement.getElementsByTagName(argChildElementName);<br />    return (Element)childNodeList.item(argSpecificationNumber);<br />  }</p>
		<p>  //***************************************************************************<br />  /**<br />   * 指定した親要素の中の全ての子要素を配列で取得します。<br />   * @param  argParentElement       親要素<br />   * @param  argChildElementName    子要素名<br />   * @return 子要素の配列<br />   */<br />  //***************************************************************************<br />  public static Element[] getChildElementList(Element argParentElement,<br />                                              String argChildElementName) {<br />    NodeList childNodeList =<br />                    argParentElement.getElementsByTagName(argChildElementName);<br />    int listCount = childNodeList.getLength();<br />    if(listCount == 0) {<br />      return null;<br />    }<br />    Element[] childElementList = new Element[listCount];<br />    for (int i0 = 0; i0 &lt; listCount; i0++) {<br />      childElementList[i0] = (Element)childNodeList.item(i0);<br />    }<br />    return childElementList;<br />  }</p>
		<p>  //***************************************************************************<br />  /**<br />   * 指定した要素の中で指定する属性の値が設定されている子要素を取得します。<br />   * @param  argParentElement    親要素<br />   * @param  argChildElementName 子要素名<br />   * @param  argAttributeName    属性名<br />   * @param  argAttributeValue   属性の値<br />   * @return 指定する属性の値が設定されている子要素で最初に取得できたもの<br />   */<br />  //***************************************************************************<br />  public static Element getChildElement(Element argParentElement,<br />                                        String argChildElementName,<br />                                        String argAttributeName,<br />                                        String argAttributeValue) {</p>
		<p>    NodeList childNodeList = argParentElement.getElementsByTagName(argChildElementName);<br />    int listLength = childNodeList.getLength();<br />    if(listLength == 0) {<br />      return null;<br />    }<br />    Element childElement = null;<br />    for (int i0 = 0; i0 &lt; listLength; i0++) {<br />      Element localChildElement = (Element)childNodeList.item(i0);<br />      String attributeValue = localChildElement.getAttribute(argAttributeName);<br />      if (attributeValue.equals(argAttributeValue)) {<br />        childElement = localChildElement;<br />        break;<br />      }<br />    }</p>
		<p>    return childElement;<br />  }</p>
		<p>  //***************************************************************************<br />  /**<br />   * 指定した要素の内容を取得します。<br />   * @param  argElement 内容を取得したい要素<br />   * @return 内容<br />   */<br />  //***************************************************************************<br />  public static String getElementContents(Element argElement) {<br />    if(argElement != null) {<br />      Text text = (Text)argElement.getFirstChild();<br />      if(text == null) {<br />        return null;<br />      }<br />      return text.getNodeValue();<br />    } else {<br />      return null;<br />    }<br />  }</p>
		<p>  //***************************************************************************<br />  /**<br />   * 指定した親要素の中で最初の子要素の内容を取得します。<br />   * @param  argParentElement 親要素<br />   * @param  argChildElementName  内容を取得したい子要素名<br />   * @return 内容<br />   */<br />  //***************************************************************************<br />  public static String getChildElementContents(Element argParentElement,<br />                                               String argChildElementName) {</p>
		<p>    Element childElement = getChildElement(argParentElement,<br />                                           argChildElementName);<br />    return getElementContents(childElement);<br />  }</p>
		<p>  //***************************************************************************<br />  /**<br />   * 指定した親要素の中で指定する属性の値が設定されている子要素の内容を取得します。<br />   * @param  argParentElement    親要素<br />   * @param  argChildElementName 内容を取得したい子要素名<br />   * @param  argAttributeName    属性名<br />   * @param  argAttributeValue   属性の値<br />   * @return 内容<br />   */<br />  //***************************************************************************<br />  public static String getChildElementContents(Element argParentElement,<br />                                               String argChildElementName,<br />                                               String argAttributeName,<br />                                               String argAttributeValue) {</p>
		<p>    Element childElement = getChildElement(argParentElement,<br />                                           argChildElementName,<br />                                           argAttributeName,<br />                                           argAttributeValue);<br />    return getElementContents(childElement);<br />  }</p>
		<p>  //***************************************************************************<br />  /**<br />   * 指定した親要素の中で最初の子要素の属性の値を取得します。<br />   * @param  argParentElement    親要素<br />   * @param  argChildElementName 子要素名<br />   * @param  argAttributeName    属性名<br />   * @return 属性の値<br />   */<br />  //***************************************************************************<br />  public static String getAttributeValue(Element argParentElement,<br />                                         String argChildElementName,<br />                                         String argAttributeName) {<br />    return getAttributeValue(argParentElement, argChildElementName, 0, argAttributeName);<br />  }</p>
		<p>  //***************************************************************************<br />  /**<br />   * 指定した親要素の中で指定した順番の子要素の属性の値を取得します。<br />   * @param  argParentElement       親要素<br />   * @param  argChildElementName    子要素名<br />   * @param  argSpecificationNumber 順番<br />   * @param  argAttributeName       属性名<br />   * @return 属性の値<br />   */<br />  //***************************************************************************<br />  public static String getAttributeValue(Element argParentElement,<br />                                         String argChildElementName,<br />                                         int argSpecificationNumber,<br />                                         String argAttributeName) {<br />    Element childElement = getChildElement(argParentElement,<br />                                           argChildElementName,<br />                                           argSpecificationNumber);<br />    return childElement.getAttribute(argAttributeName);<br />  }<br />}<br /></p>
<img src ="http://www.blogjava.net/songfei/aggbug/36346.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/songfei/" target="_blank">天外飞仙</a> 2006-03-20 15:57 <a href="http://www.blogjava.net/songfei/articles/36346.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item></channel></rss>