PBDOM操作XML文档轻松入门2008-03-06 15:13本文对PBDOM技术进行相关介绍,但并不涉及XML的基础知识,建议阅读者对下述相关术语有一定了解: Document(文档), DTD(文档类型定义), schema (大纲),Element(元素), attribute(属性), processing instruction (处理命令), entity(实体)。
本文主要包括以下内容:1、为什么要使用PBDOM以及怎样创建PBDOM2、PBDOM主要用于那些地方3、如何使用PBDOM编程4、PBDOM和其他XML解析(parser)技术的比较一、什么是DOM◆文档对象模型(Document Object Model)1、作为一项W3C规范,XML DOM存在目的是为不同类型的应用程序提供一个标准的编程接口,它被设计可以跨平台、跨语言使用。
2、我们可以利用XML DOM创建XML文档并操纵其结构,增加、修改、删除元素。
3、程序中调用XML解析器载入XML文档到内存中。
当文档被载入后,可以通过进入DOM检索和操作相关信息。
4、DOM 保存了XML文档树,文档(document)元素位于整棵树的最顶层。
该元素可以有一到多个子节点来保存树的结构。
可以参阅以下网站: /dom/ 来了解更多的关于XML Document Object Model的内容。
二、什么时候应该使用DOM工具◆当你需要做下列事情的时候,你应该想到XML DOM的1、在一个或者多个XML文档之间移动元素2、创建新的元素并且在XML文档的任意位置插入3、操作元素并重新插入其到XML文档其他位置4、导入内嵌数据结构& . pb9中,数据窗口现在可以通过XML导出内嵌数据结构(nested data structures).三、什么是PBDOM◆PowerBuilder 文档结构模型(PowerBuilder Document Object Model)1、PBDOM是通过PBNI扩展出来的,用于操作XML数据,并针对PowerScript作了优化2、在程序中模型是通过DOM的抽象来表示XML数据。
(A programming model to represent XML data –an abstraction of DOM)3、底层是对Apache Xerces/C++的封装。
四、PBDOM的设计目标1、简单易用(Be straightforward for PowerBuilder programmers)2、可以利用PowerScript的强大语言能力(如对象、方法重载、数据等)3、在可能的情况下,隐藏了XML底层的复杂实现(Hide the complexities of XML wherever possible)4、原有的DOM在pb下使用不够直观(DOM is unintuitive to a PowerBuilder programmer)五、使用PBDOM初步◆PBDOM设置1、添加pbdom90.pbd(%SYBASE%\Shared\PowerBuilder)到工程的pbl列表中2、%SYBASE%\Shared\PowerBuilder应该在系统路径或者应用程序的路径中(也就是pbdom要使用此路径下的pbdom90.dll, pbxerces90.dll、xerces_2_1_0.dll文件,同样,当程序发布时候也需要)六、PBDOM类的使用◆如图所示,反映了PBDOM类的组成和继承关系,可以看到,几乎所有的PBDOM类都继承自PBDOM_Object(除了PBDOM_Builder和PBDOM_Exception)1、PBDOM_Document◆构建PBDOM举例1.1 直接构建(XML documents can be created from scratch)PBDOM_Document docPBDOM_Element rootdoc = CREATE PBDOM_Document root = CREATE PBDOM_Elementroot.SetName( "root" )root.SetText( "this is the root" )doc.AddContent( root )1.2 从文件、字符串、DataStore中载入PBDOM_Builder builderdoc = builder.BuildFromString( "<foo>bar</foo>" ) doc = builder.BuildFromFile( "c:\foo\bar.xml"doc = builder.BuildFromDataStore( l_ds)2、PBDOM_Element2.1 遍历元素PBDOM_Element root, children[], first// Get the root element of the documentroot = doc.GetRootElement()// Get an array of all child elementsroot.GetChildElements( children )// Get only elements with a given nameroot.GetChildElements( "name", children )// Get the first element with a given namefirst = root.GetChildElement( "name" )注意:上例中得到的元素数组是联动的!(The element array is live!)即:◆ 修改数组中的元素,同样会作用到父文档◆ 返回的数组是有界的(Once the array is returned, it is now bounded)◆ 在数组中增加新元素时,需要一个SetContent()方法调用2.2 移动元素// PBDOM_Document docOne,docTwoPBDOM_Element movablemovable = CREATE PBDOM_ElementMovable.SetName( "movable" )docOne.AddContent( movable ) // addmovable.Detach() // removedocTwo.addContent( movable ) // add again注意:1、只要是从PBDOM_Object继承的对象,都可以调用Detach()方法(如Comments、ProcessingInstructions、Elements (and their content)等等)2、PBDOM元素对象不是永久的捆绑在它的父文档上的(PBDOM elements aren't permanently tied to their parent document)2.3 符合规格(Always well-formed)PBDOM_Element构造器以及setter方法会检查元素是否符合规格:elem.SetName( "Spaces are illegal" )AddContent()方法也会从以下几个方面进行检查:◆ 结构---树中没有循环(Structure –no loops in any tree) ◆ 只有一个根节点元素(One and only one root element)◆ 相容的命名空间(Consistent namespaces)3、PBDOM_Attribute3.1 操作元素属性◆ 元素可以有多个属性<table width="100%" border="0"></table>// Get an attributels_width = table.GetAttributeValue( "width" ) // orls_width = table.GetAttribute ( "width" ).GetText()// Attributes can be typedli_border = table.GetAttribute( "width" ).GetIntValue()// Set an attributetable.SetAttribute( "cellspacing", "0" )// Remove an attributetable.RemoveAttribute( "cellspacing" )// Remove all attributesPBDOM_Attribute empty[]table.SetAttributes( empty ) // the PowerScript way4、PBDOM_Text4.1 操作元素文本内容<description>cool demo</description>// the text is directly available –returns// "~r~ncool demo~r~n"ls_desc= elem.GetText()// two convenience methodsls_desc= elem.GetTextTrim()// returns "cool demo"ls_desc = elem.GetTextNormalize()// returns "cool demo"// text can be changed directlyelem.SetText( "a new description" )5、PBDOM_Object5.1 操作有混合内容的元素<description><!–comment --><?convert units="metric" ?>cool demo</description>PBDOM_Object content[]desc.GetContent( content )FOR i = 1 TO UpperBound( content )CHOOSE content[i].GetObjectClassString()CASE "pbdom_comment"// ...CASE "pbdom_processinginstruction"// ...END CHOOSENEXT6、PBDOM_ProcessingInstruction6.1 使用处理命令(Processing instructions)<? xml-stylesheet type="text/xsl"href="foo.xsl"_fcksavedurl=""foo.xsl"" ?>{------target------} {----------------data---------------}// Get target (e.g., "xsl-stylesheet")ls_target = pi.GetTarget()// Get data (e.g., 'type="text/xsl"href="foo.xsl"')ls_data = pi.GetText()// Get individual values as attributesString names[]pi.GetNames( names )FOR i = 1 TO UpperBound( names )MessageBox( names[i], pi.GetValue( names[i] )NEXT7、PBDOM and 命名空间(Namespaces)<xsl:stylesheet version="1.0"xmlns:xsl="/1999/XSL/Transform"><xsl:variable name="ffsection" select="//SITE_SECTION<xsl:template name="TopNav">......</xsl:template></xsl:stylesheet>String ls_elementPBDOM_Element template// get element name and namespace –return "xsl:template"template = root.GetChildElement( "template" )ls_element= template.GetNamespacePrefix() +":"+ template.Getname()// get element by name and namespacetemplate = root.GetChildElement( "template", "xsl","/1999/XSL/Transform")七、PBDOM vs. the Competition◆Apache Xerces/COMXerces 是现在PBDOM底层使用的XML解析器,但对PowerBuiler用户来说使用不直观。