但在拍卖数据库中储存的结构化数据方面,示例情势是表、视图、索引那样的数据库对象的聚集

Oracle 9i产品协助文档:

在 Oracle 数据库 10g 第 2 版中,Oracle
引入了八个与该数据库集成的全职能自带 XQuery
引擎,该引擎可用以完成与支出协理 XML 的应用程序相关的各个任务。XQuery
是一种用于拍卖 XML 数据模型的查询语言,它实际可操作任何类型的可用 XML
表达的数目。固然 Oracle XQuery
实施使你能够使用数据库数据和外部数据源,但在处理数据库中存款和储蓄的结构化数据方面,Oracle
XML DB 经常可以分明拉长质量。

http://docs.oracle.com/cd/B10501_01/index.htm

正文提供的示范不仅示范了在如何地方下以及哪些使用 XQuery 查询、创设和转移
XML,而且还以身作则了何等监督和剖析 XQuery
表明式的特性执行,从而找到更快捷的办法来处理同一工作负荷。

可依照本人索要展开查询,包蕴了众多的文书档案。

依据关周详据创设 XML

 

在要求的情形下(例如,向 Web 服务发送结果),您大概要依照关全面据营造XML。要在 Oracle 数据库 10g 第 2
版此前的版本中成功此职分,经常须求运用 SQL/XML 生成函数,如
XMLElement、XMLForest 和 XMLAgg()。在 Oracle 数据库 10 g 第 2
版中,XQuery 将比那个函数更为连忙。具体而言,在 XQuery 表明式内部采用ora:view XQuery 函数,您能够查询现有的涉及表或视图以及及时塑造XML,从而无需经过关周全据显式创立 XML 视图。列表 1 中的 PL/SQL
代码演示了怎么着接纳 ora:view 基于示例数据库格局 HSportage的默许职员和工人涉嫌表中贮存的数码营造 XML 文书档案。

Sample Schemas的目录:

列表 1:使用 ora:view 基于关全面据创设 XML

http://docs.oracle.com/cd/B10501_01/server.920/a96539/toc.htm

BEGIN
IF(DBMS_XDB.CREATEFOLDER('/public/employees')) THEN
DBMS_OUTPUT.PUT_LINE('Folder is created');
ELSE
DBMS_OUTPUT.PUT_LINE('Cannot create folder');
END IF;
COMMIT;
END;
/
DECLARE
XMLdoc XMLType;
BEGIN
SELECT XMLQuery(
'for $j in 1
return (
{
for $i in ora:view("HR", "employees")/ROW
where $i/EMPLOYEE_ID <= 102
return (
{xs:string($i/EMPLOYEE_ID)}
{xs:string($i/LAST_NAME)}
{xs:integer($i/SALARY)}
)} )'
RETURNING CONTENT) INTO XMLdoc FROM DUAL;
IF(DBMS_XDB.CREATERESOURCE('/public/employees/employees.xml', XMLdoc)) THEN
DBMS_OUTPUT.PUT_LINE('Resource is created');
ELSE
DBMS_OUTPUT.PUT_LINE('Cannot create resource');
END IF;
COMMIT;
END;
/

 

在列表 1 中的第三个 PL/SQL 进度中,您只是在 XML
消息库中开创了一个新文件夹。在该信息库文件夹中,您随后将积存此处呈现的第三个PL/SQL 进程中成立的 XML 文书档案。第三个 PL/SQL 进程首首发出 SELECT
语句,该语句使用 XMLQuery SQL 函数基于关周全据营造 XML。对于 XQuery
表明式(XMLQuery 在此地将其用作参数)而言,请留意嵌套的 FLWO哈弗表明式中使用的 ora:view XQuery 函数。在该示例中,ora:view
获取多个输入参数,即“HLAND”和“employees”,它们提醒该函数查询属于 HLX570数据库格局的职员和工人表。因此,ora:view 将回到3个象征 H景逸SUV.employees
表行的职工 XML
文书档案系列。但为了省去结果文书档案中的空间,只将前四个职员和工人记录传递给结果系列。那是透过在
FLWOHighlander 表明式的 where 子句中内定 $i/EMPLOYEE_ID <= 102
而落实的。请小心 FLWO兰德索罗德 表明式的 return 子句中利用的 xs:string()
xs:integer() XQuery 类型表明式。实际上,此处使用的这三个 XQuery
表明式不仅将 XML
节点值转换为相应的门类,而且还将领到这几个节点值。随后,生成的职工 XML
文书档案作为 employees.xml 保存到事先在列表 1 中另三个 PL/SQL 进度中创设的
/public/employees XML 消息库文件夹。要保管此操作已成功,可实施以下查询:

萨姆ple Schemas的文书档案(示例方式的表及介绍):

SELECT XMLQuery('for $i in fn:doc("/public/employees/employees.xml")
return;
$i'
RETURNING CONTENT) AS RESULT FROM DUAL;

http://docs.oracle.com/cd/B10501_01/server.920/a96539.pdf

该查询应生成以下输出:

 


100
King
24000


101
Kochhar
17000


102
De Haan
17000

重重年来,Oracle教师、管理员、程序员、以及用户为了学习、测试或调整他们的数据库,都一直在动用那个值得依靠的SCOTT形式展开着简单地询问、更新、以及去除操作。这个方式就是大家所说的以身作则形式。示例方式是表、视图、索引这样的数据库对象的成团,并且随着预先供了象征小框框依旧中等规模公司的数量。

在以上 XQuery 中,fn:doc XQuery 函数用于访问 Oracle XML DB
音信库中蕴藏的单个 XML 文书档案。但若是要拍卖部分颇具同等或一般结构的 XML
文书档案(存款和储蓄在同一 XML
新闻库文件夹中),应该如何是好?那种景色下,另贰个用来拍卖 XML
音讯库财富的 XQuery 函数(即
fn:collection)大概会派上用场。本文稍后将介绍多少个有关怎样选择fn:collection XQuery 函数的言传身教。

乘机最新版本的Oracle数据库Oracle
9i的面世,又推荐了崭新的一组示例方式,它们的指标是扩充SCOTT形式向用户提供的效应。全体这几个情势一起形成了相同的虚构集团的一某些,它们各自都有温馨的事体中央。例如,人力财富部、订单输入部门以及发货部门都有分手的格局。

查询 XMLType 数据

注意:

伟德国际1946,XQuery 使你能够操作基于 XML
形式以及非基于格局的多寡。以下示例演示了哪些使用 XMLTable 函数从 OE
演示数据库格局中查询基于 PurchaseOrder XML 方式的 XMLType 表。

此时此刻hr已经锁定了(即lock)。要求进行以下脚本:

SELECT ttab.COLUMN_VALUE AS OrderTotal FROM purchaseorder,
XMLTable(
'for $i in /PurchaseOrder
where $i/User = "EABEL"
return;

{$i/Reference}

{fn:sum(for $j in $i/LineItems/LineItem/Part
return ($j/@Quantity*$j/@UnitPrice))}

'
PASSING OBJECT_VALUE
) ttab;
SQL> connect system/zyf;

已连接。

SQL> alter user hr account unlock;

用户已更改。

SQL> alter user hr identified by hr;

用户已更改。

SQL> connect hr/hr;

已连接。

SQL> select table_name from user_tables;

TABLE_NAME

------------------------------

COUNTRIES

DEPARTMENTS

EMPLOYEES

JOBS

JOB_HISTORY

LOCATIONS

REGIONS

已选择7行。

在上述示例中,您在 XMLTable 函数的 PASSING 子句中动用 OBJECT_VALUE
虚拟列将 purchaseorder 表作为左右文项传递给那里使用的 XQuery
表明式。XQuery 表明式总计用户 EABEL
请求的每一个购买订单的累计,并为处理的各种订单生成三个 OrderTotal XML
成分。要拜访生成的 XML,请使用 SELECT 列表中的 COLUMN_VALUE
虚拟列。最终的出口应如下所示:

4.1 SCOTT模式

所提供的SCOTT形式能够提供部分示例表以及数据,来展现数据库的一些特点。它是一个非常不难的情势,如图4-1数据结构图所示(通过PowerDesign逆向工程转换为数据库模型)。

图4-1 SCOTT情势数据结构图

 伟德国际1946 1

怎么要将那么些格局命名为SCOTT呢?SCOTT/TIGERAV4是Oracle版本① 、2和3时期的Oracle数据库的中期用户名/密码组合。SCOTT是指Oracle公司的泰斗程序员BruceScott。当然,TIGE大切诺基是Bruce养的猫的名字。

SCOTT方式中所展现的数据库性子平日被认为是多数关周详据库产品中的重要特征。要是想要真实地显示Oracle数据库的作用,就要强化那些示例!

ORDERTOTAL
-------------------------------------------------------------

EABEL-20021009123338324PDT
1328.05


EABEL-20021009123335791PDT
2067.15


EABEL-20021009123336251PDT
289.6


EABEL-20021009123336382PDT
928.92

4.2 Oracle 9i示例形式

Oracle技术能够采纳于各个不一致的条件中。技术消除方案的五个使用极端意况是,高速在线事务处理和数据库仓库。就算用户能够行使二个格局,彰显什么在同一的表中实现在线事务处理和数据仓库。可是用户毫无容许行使这种艺术完结实用的缓解方案。大家在当今的产业界中不时可以发现,为了消除实际世界中的分化计算必要,平时在独立的数据库实例中会存在不一样的形式,或许在互连网上会有大气分布式数据库。新的Oracle
9i示例情势模型极好地对这些场景建立模型。

Oracle
9i示例方式试图模型化二个切实可行世界中有所一名目繁多典型业务部门的销售团队。那么些差异的部门有着区其余消息技术须要,每叁个示范方式都选拔了不一样的Oracle技术来解决它们分其他标题。其余,各个情势设计方案都指向一定的技艺用户。这么些格局如下:

  • H宝马7系——人力财富。
  • OE——订单输入。
  • PM——产品媒体。产品媒体在数据库中贮存了商行种类产品的连带多媒体内容,能够用来在Web上表露以及打印。PM利用了Oracle
    Intermedia,它尤其陈设用来拍卖宣布音频、录制以及可视数据的多媒体领域。其余,PM也一再地接纳了LOB列类型。
  • QS——队列运送。运送部门负责记录公司向客户实行的出品运载情形,并且选择陆个格局来成功那项工作。QS、QS_ES、QS_WS、QS_OS、QS_CB和QS_CS构成了队列运送方式的聚集。
  • SH——销售历史。

要博得同样的结尾结果,能够改用 XMLQuery 函数。但假诺将上一个演示中接纳的
XQuery 表达式参数传递给 XMLQuery(如下所示):

4.2.1 深刻座谈种种形式

SELECT XMLQuery('for $i in /PurchaseOrder
where $i/User eq "EABEL"
return 
{$i/Reference}

{fn:sum(for $j in $i/LineItems/LineItem/Part
return ($j/@Quantity*$j/@UnitPrice))}

'
PASSING OBJECT_VALUE
RETURNING CONTENT)
FROM purchaseorder;

1. 人力能源

人力财富形式,或然H奥德赛情势,负责管理部门、雇员、工作以及薪酬音讯。图4-2浮现了H奥迪Q7格局的详尽数据结构图示。

伟德国际1946 2

则 XQuery 表明式重回的空类别将与 purchaseorder
表联接,从而包涵在查询总计果集中。实际上,那象征输出将不仅仅含有为用户
EABEL 请求的订单生成的 OrderTotal 成分,而且还含有为 purchaseorder
表中蕴藏的具有其余订单生成的空行(暗许景况下,purchaseorder 表包涵 132
行)。从结果集中拔除空行的法子之一是在 SELECT 语句的 WHERE 子句中利用
existsNode SQL 函数,而不是在 XQuery 表明式中采纳 WHERE 子句,如下所示:

2. 订单输入

订单输入(Order
Entry)方式,大概OE方式,能够用来管理公司从事商务活动的一一渠道中的客户、销售订单以及产品仓库储存。

图4-3详尽描写了OE形式的数据结构。就像笔者辈原先掌握的,与人力能源情势比较,订单输入形式越发复杂。

伟德国际1946 3

图4-3 OE格局数据结构

OE方式会记录产品仓库储存。大家将会储存任意钦赐仓库中钦定产品的多少。在商店中会有多少个仓库,所以要采用地方标识符提出其地理区域。在WAREHOUSES表中还有二个Oracle
Spatial列,它为大家提供了应用Oracle Spatial空间技术的钥匙。

Oracle Spatial是在数据库中补助地点数据和地理数据的技巧。

在OE情势中,要求顺便提供提及五个数据库对象模型:

  • CUST_ADDRESS_TYP。那是三个在CUSTOME中华VS表中动用的靶子类型。它含有了累累与客户地址有关的性情。

SQL> desc cust_address_typ;

名称 是否为空? 类型

----------------------------------------- -------- 

STREET_ADDRESS VARCHAR2(40)

POSTAL_CODE VARCHAR2(10)

CITY VARCHAR2(30)

STATE_PROVINCE VARCHAR2(10)

COUNTRY_ID CHAR(2)
  • PHONE_LIST_TYP。那是三个VA兰德WranglerCHASportage2(25)的VA奥迪Q3RAY。这么些VAHighlanderRAY在CUSTOMETucsonS表中作为独立的列存储,能够用来存款和储蓄最多5个电话号码。

SQL> desc phone_list_typ;

phone_list_typ VARRAY(5) OF VARCHAR2(25)

OE情势是二个很好的示范,它显得了正式的供应协会只怕电脑零售商店能够动用什么办法去管理它们完整订单处理进度。通过采取订单输入表中的多少,销售团队就足以向地下的客户提供规范的出品音信,接受销售订单,量化订单收入,存款和储蓄客户消息,为分裂地理地点订购产品的客户提供准确的仓库储存新闻,以及其余服务。

SELECT XMLQuery('for $i in /PurchaseOrder
return 
{$i/Reference}

{fn:sum(for $j in $i/LineItems/LineItem/Part
return ($j/@Quantity*$j/@UnitPrice))}

'
PASSING OBJECT_VALUE
RETURNING CONTENT) AS ordertotal
FROM purchaseorder
WHERE existsNode(OBJECT_VALUE, '/PurchaseOrder[User = "EABEL"]') = 1;

3. 成品媒体

出品媒体(Product
Media)格局,可能PM格局,用于管理描述公司出品的多媒体数据。摄像、音频和图像那样的在线媒体都能够随输出的传播媒介数据类型存储在数据库中。那是大家要尤其探究的格局之一,它重视于多媒体内容,以及Oracle
Intermedia所提供的效应。

注意:

Oracle Intermedia是Oracle数据库帮忙多媒体内容类型的机件。

除开Intermedia数据存款和储蓄以外,PM情势还特别注重LOB列类型的施用来储存数据。

产品媒人体模型式是Oracle 9i使用名为Oracle
Intermedia的Oracle技术化解实际世界商务供给的卓绝示例。例如,大家虚构的小卖部就能够储存多媒体数据或许输出多媒体数据。由此,产品媒人体模型式中的示例能够形成如下工作:

  • 为Oracle中利用Web公布的始末存款和储蓄缩略图和完全尺寸的图像。
  • 在Oracle中贮存音频剪辑。
  • 在Oracle中蕴藏录像剪辑。
  • 对图像类型举办拍卖,以便转换来与Web包容的图像类型

行使Oracle
Intermedia,一些曾经很难达成的任务就变得相对简单。图4-4意味着为产品媒人体模型式,以及它对订单输入表PRODUCT_INFORMATION的引用。

伟德国际1946 4

图4-4 PM情势数据结构

PRINT_MEDIA表拥有2个指标类型(ADHEADE凯雷德_TYP),以及在表的依次记录中储存的对象嵌套表(TEXTDOC_TAB)。

ORDSYS.ORD__列都以二个Intermedia对象类型。这几个Intermedia对象类型不仅能够储存图像、音频、录制那样的二进制数据;还能储存各个与多媒体类型有关的元数据。

SQL> desc ordsys.ordimage;

上述查询与本有的初步的 XMLTable 示例生成相同的输出。

4. 系列运送

大家的虚构公司想要使用新闻系统,以造福在线客户开始展览自助订货。当客户初阶化订货的时候,系统就必要建立订单,向客户提供账单,并且要保险能够依照客户的岗位,通过适当的地方发送订货。

QS_CS形式有多少个名为OPRADODE科雷傲_STATUS_TABLE的表,能够储存订单状态。那是在全部队列运送格局安装进程中唯第二建工公司立表(除了通过高档队列API建立的队列表以外)。大家不会显得与表有关的数据结构图,而是要探讨为队列运送情势所建立的类别系统中的新闻流程。

图4-5所示流程图示中可以看到,为了提供三个分明、直观的订座——发货——结算循环,要在机构中间什么传递音信。

伟德国际1946 5

图4-5 为队列运送(QS)方式在队列系统中树立的音讯流程

方方面面都要从图示顶部的订单输入开始。Oracle
Input(订单输入)进度所生成的订单会放入New Order
Queue(新订单队列)中。那么些行列要Oracle
Entry应用处理,然后会将订单放到Booked Orders
Queue(登记订单队列)中。再将Booked Orders
Queue中的订单发往适中的运送宗旨(East(南边)、韦斯特(西部)大概Overseas(国外)),以及客户服务机关。

在那时,运送宗旨就会吸收要到位的订单,并且向客户发送订货,而且客户服务单位也会意识到订单的场馆。在适宜的运输核心,Shipping
Center(运送中央)应用就会承担发送订货,可能将预定调整回订单状态。一旦获得了成品,就会发送退回为订单状态的产品,并且将订单放到shipped
orders(已运送订单)队列中。

当订单发送之后,就会通过shipped orders
gueue公告客户服务和客户结算部门,并且向客户发送账单。经过结算的订单会放在Billed
Orders(已结算订单)队列中,它会通告客户服务机关,然后就能够成功订单处理进程。

查询 Oracle XML DB 消息库中的 XML 数据

5. 售货历史

今天商务条件中的公司曾经发现,除非人们能够使用一种有含义并且即时的方式,依据新闻变化精确的仲裁报告,不然世界上的持有销售音信都是毫无价值的。决策援救(decision
support)正是用来叙述在开展裁定的经过中国国投息技术利用的术语。

销售历史方式是八个古板数据仓库的以身作则。表会依据正方形形式(star
schema)设计举行集团,在那种措施下,会有1个大的SALES表位于中央,SALES表的外侧还会有一对小的查询表,大概维数(dimension)表。SALES表常常会有雅量的数量(全部的销售实时),而维数表绝对于SALES表来讲会不大。

图4-6的数据结构图呈现了销售历史格局:

伟德国际1946 6

图4-6 销售历史格局数据结构

为访问 Oracle XML DB 消息库中蕴藏的 XML 数据,Oracle XQuery 引入了
fn:doc 和 fn:collection XQuery 函数。使用 fn:doc,您能够查询 XML
新闻库中存款和储蓄的单个 XML 文书档案,而 fn:collection
使您能够访问同一音讯库文件夹中储存的三个 XML 文书档案。

4.2.2 渐进学习方法

依据差异的受众组织情势的方式得以鼓励新的Oracle用户通过结构化的法子学习技能。例如,初学者能够从人力能源开首。那能够让她理解关系概念、查询数据、数据库操作语言、数据库定义语言、以及部分任何基本概念。

当新Oracle用户驾驭了人力财富形式之后,能够持续分析订单输入方式。在这一个新情势中,他将会碰着对象类型、XML支持、Oracle
Spatial、以及其余部分比较高档的数据库性情。

接下去,用户能够分析任何形式所提供的一定领域。多媒体育专科学校家能够深切学习产品媒人体模型式。设计算与发放布-订阅型基于音信的系统的用户能够发现,队列运送形式在她们起先攻读Oracle高级队列的时候将会十二分有帮带。数据仓库的热衷者最好去分析和领会销售历史格局。

正如本文从前(参阅使用关周密据塑造 XML部分)介绍的演示所示范,使用
fn:doc 格外不难直接。它拿走表示新闻库文件能源 (U中华VI) 的字符串并重回该 U牧马人I
指向的文书档案。要打听 fn:collection XQuery
函数的效应,同一文件夹中最少应当七个信息库文件。若是已经运营了列表 1中的代码,则已经成立了 /public/employees 新闻库文件夹并在其间存储了
employees.xml 文件。因而,您将急需在该文件夹中至少再次创下制1个 XML
文件,然后才能试用 fn:collection。列表 2 中的 PL/SQL 代码基于
SCOTT/TIGE哈弗 演示数据库方式的 dept 和 emp 表存款和储蓄的关全面据塑造XML,然后将转变的 XML 文书档案作为 acc_dept.xml 保存到 /public/employees
音信库文件夹。要运营列表 2 中的 PL/SQL 进程,请确定保障以 SCOTT/TIGEOdyssey的地位登录。

4.2.3 发现越多关于示例形式的内容

列表 2:基于关周全据创设 XML 并将其保存到 XML 消息库

1. 数据库对象描述

在这一部分中,大家将会浏览数据库,找到属于示例情势下的目的,然后利用SQL查询直接从数据库中得到那一个指标的定义。

注意:

以下试验部分所需的万事脚本都足以从http://www.wrox.com/的本书可下载代码中取得。

试验:获取数据库列表

将以下脚本保存到用户本地硬盘上名为dbls.sql的文书中(C:\oracle\ora92\bin,即sql*plus工作目录)

column object_name format a30

column tablespace_name format a30

column object_type format a12

column status format a1

break on object_type skip 1

select object_type,object_name,

decode(status,'INVALID','*','') status,

tablespace_name

from user_objects a,user_segments b

where a.object_name=b.segment_name(+)

and a.object_type=b.segment_type(+)

order by object_type,object_name

/

column status format a10

运行以下代码可取得数据库对象列表:

SQL> connect hr/hr;

已连接。

SQL> @dbls
DECLARE
XMLdoc XMLType;
BEGIN
SELECT XMLQuery(
'for $j in ora:view("SCOTT", "dept")/ROW
where $j/DEPTNO = 10
return ( 
{$j/DEPTNO,
$j/DNAME}
 {
for $i in ora:view("SCOTT", "emp")/ROW
where $i/DEPTNO = $j/DEPTNO
return (

{$i/EMPNO,
$i/ENAME,
$i/SAL}
)} 

)'
RETURNING CONTENT) INTO XMLdoc FROM DUAL;
IF(DBMS_XDB.CREATERESOURCE('/public/employees/acc_dept.xml', XMLdoc)) THEN
DBMS_OUTPUT.PUT_LINE('Resource is created');
ELSE
DBMS_OUTPUT.PUT_LINE('Cannot create resource');
END IF;
COMMIT;
END;
/

2. 自解释情势

Oracle提供了一种能够让表的持有者在数据库中存款和储蓄表大概列的纯文本注释的章程。在示范格局安装时期,每种形式都存有2个本子,能够为它们分其他表和列建立这么些注释。那足以采取SQL命令CREATE
COMMENT达成。当中注释样本如下:

COMMENT ON TABLE jobs

IS ‘jobs table with job titles and salary ranges.Contains 19 rows.

References with employees and job_history table.’;

那时候,/public/employees
新闻库文件夹应蕴含八个公文:acc_dept.xml(由列表 2 中的 PL/SQL
代码生成)和 employees.xml 文件(由列表 1 中的代码生成)。由于那么些 XML
文书档案存款和储蓄在同等新闻库文件夹中,由此可以使用 fn:collection 函数访问八个XML 文书档案中贮存的职工音讯。但是,即使那些 XML 文书档案均含有员工 XML
成分(那一个要素实际上具有同样结构),但 XML 文档本人的结构迥然不一样。在
employees.xml 中,文书档案根成分为 EMPLOYEES,而 acc_dept.xml 将 DEPA奥迪Q7TMENT
用作根元素。要化解此难点,能够经过 XQuery 使用 XPath // 构造,从而导航到
XML 文书档案中的有个别节点,而不用钦命该节点的适用路径。以下示例演示了如何在
XQuery 表明式中使用 XPath // 构造:

4.3 小结

作品依据本人掌握浓缩,仅供参考。

摘自:《Oracle编程入门经典》 北大东军事和政院学出版社 http://www.tup.com.cn/

SELECT XMLQuery(
'for $i in fn:collection("/public/employees")//EMPLOYEE
where $i/SAL >= 5000
order by $i/ENAME
return;
$i'
RETURNING CONTENT) FROM DUAL;

该协会应生成以下输出:

102
De Haan
17000


7839
KING
5000


100
King
24000


101
Kochhar
17000

您能够看来,以上输出包括从 employees.xml 和 acc_dept.xml 中取得的职工
XML 成分,那几个成分表示薪俸大于或等于 5,000 新币的职工。

将 XML 分解为关周详据

设若应用程序处理关周密据而非 XML,而你须要拜访的多少以 XML
格式存储,则将 XML
分解为关全面据大概会尤其实惠。继续拓展上一些的演示,您能够运用 SQL
函数 XMLTable 将职工 XML 成分分解为虚拟表的单个列,如下所示:

SELECT emps.empno,emps.ename, emps.sal FROM 
XMLTable(
'for $i in fn:collection("/public/employees")//EMPLOYEE
where $i/SAL >= 5000
return;
$i'
COLUMNS empno NUMBER PATH '/EMPLOYEE/EMPNO',
ename VARCHAR2(30) PATH '/EMPLOYEE/ENAME',
sal NUMBER PATH '/EMPLOYEE/SAL') emps;

该查询将扭转以下输出:

EMPNO ENAME SAL
----- -------------- ----------
7839 KING 5000
100 King 24000
101 Kochhar 17000
102 De Haan 17000

查询外部数据源

选拔 XQuery,能够依据 XML 数据以及可以用 XML 表示的非 XML 数据生成 XML
文档,无论其岗位怎么:无论是存款和储蓄在数据库中、置于网站上、即时创造恐怕存款和储蓄在文件系统中。但要注意,Oracle
XML DB 为针对数据库中储存的数码开始展览的 XML
操作提供了老大高的质量和可伸缩性。因此,假若你能够完全控制所处理的多寡,则最好将它移动到数据库中。

正如您之前面包车型大巴示范中打听到的,在 Oracle XQuery 实施中,doc 和 collection
XQuery 函数用于访问 Oracle XML DB 音信库中贮存的 XML 文书档案。能够透过
XMLTable 和 XMLQuery SQL 函数中的 PASSING
子句动态绑定外部数据源。考虑以下示例。借使你的商店要为这几个从事于 XQ
项目标职工支付奖金。因而,财务部发表了 empsbonus.xml
文件,其中包括有身份得到奖金的职员和工人列表以及该列表中输入的各样职工的奖金多少。empsbonus.xml
文件或然如下所示:

100
1200


101
1000

在实质上景况中,以上的 XML
文件可能置于网站上(因而得以因而互连网获取)、以文件方式储存在地头文件系统中,或以文件能源情势储存在
Oracle XML DB
信息库中。就本示例而言,该文件位于网站上。为简便起见,能够在目录(Web
服务器在其间蕴藏可从 Web
看到的文书档案)中开创二个职工文件夹,然后在该公文夹中插入 empsbonus.xml
文件,以便能够通过以下 U安德拉L 访问 empsbonus.xml 文件:

http://localhost/employees/empsbonus.xml

接下去,如果您要求依照 empsbonus.xml
文书档案中蕴藏的多少创制一个表格。在该报表中,您恐怕不仅要含有列表中显得的奖金数额以及各样员工的职员和工人ID,还要包蕴他/她的姓名。因而,可以率先应用以下查询生成一个新的 XML
文档(假设你以 H科雷傲/H帕杰罗 的身价连接):

SELECT XMLQuery(
'for $k in 1
return (
 {for $i in ora:view("employees")/ROW,
$j in $emps/EMPLOYEES/EMPLOYEE
where $i/EMPLOYEE_ID = $j/EMPNO
return (
{xs:string($i/EMPLOYEE_ID)}
{xs:string(fn:concat($i/FIRST_NAME, " ", $i/LAST_NAME))}
{xs:integer($j/BONUS)}
)} )'
PASSING xmlparse (document httpuritype
('http://localhost/employees/empsbonus.xml').getCLOB()) as "emps"
RETURNING CONTENT).getStringVal() as RESULT FROM DUAL;

上述查询是3个有关怎样行使 XQuery 基于 XML 和非 XML
数据(以不一致的法门从分化的数据源中检索)生成 XML
文书档案的示范。具体而言,使用 ora:view() 函数访问 HR 演示格局中的默许
employees 关系表,并使用 PASSING 子句中的 httpuritype() 函数借助于
HTTP 访问 empsbonus.xml 文书档案。然后,在 FLWOR 表明式的 return
子句中构建新的 XML 文档。最终,将获取以下 XML 文书档案:


100
Steven King
1200


101
Neena Kochhar
1000

缓解品质难点

正如你从眼下的有的中明白到的,XQuery 是一种用于查询 Oracle 数据仓库储存款和储蓄的
XML 内容的连忙方法 – 无论你是拍卖地点存款和储蓄的 XMLType
数据只怕查询基于关周全据营造的 XML
视图。但据悉对数码应用的仓库储存类型的不等,XQuery
表明式的实施性能大概截然不一样差异。尤其是,Oracle XML DB 能够优化基于由
ora:view 函数成立的 SQL/XML 视图而营造的 XQuery 表明式。对于 XMLType
表或列中储存的 XML 数据,只可以对选择结构化(对象-关系)存款和储蓄技术存款和储蓄的基于
XML 情势的 XMLType 数据开始展览 XQuery 优化。

所挑选的仓库储存模型并非是潜移默化 XQuery
表明式执行品质的绝无仅有要素。在有个别景况下,XQuery
表达式本人的结构也或者导致品质难点。要监察和控制 XQuery
表明式的习性,能够打印并检查关联的 EXPLAIN PLAN。在 SQL*Plus
中,只需安装 AUTOTRACE 系统变量,即可打字与印刷 SQL
优化程序行使的施行路径。但要执行该操作,请确认保证创设 PLUSTRACE
脚色,然后将其予以连接到数据库所选拔的用户。有关怎么样举行此操作的音讯,请参阅
Oracle 数据库 10g 第 2 版 (10.2) 文书档案中《SQL\Plus
用户指南和参考》一书中的“调整
SQL\
Plus”一章。以下示例演示了哪些通过检查 EXPLAIN PLAN
生成的实践布置来收获利益。要是你曾经将 PLUSTRACE 剧中人物赋予暗中认可用户 OE,以
OE/OE 的身价登录并运营以下查询:

SET AUTOTRACE ON EXPLAIN
SELECT count(*)
FROM oe.purchaseorder, XMLTable(
'for $i in /PurchaseOrder/User
where $i = "CJOHNSON"
return $i'
PASSING OBJECT_VALUE) ptab;

那将转变以下输出:

COUNT(*)
----------
9
Execution Plan
---------------------------------------------
Plan hash value: 4046110317
--------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
--------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 226 | 29 (0) | 00:00:01 |
| 1 | SORT AGGREGATE | | 1 | 226 | | |
| 2 | NESTED LOOPS | | 10782 | 2379K | 29 (0) | 00:00:01 |
|* 3 | TABLE ACCESS FULL | PURCHASEORDER | 1 | 226 | 5 (0) | 00:00:01 |
| 4 | COLLECTION ITERATOR P| XMLSEQUENCEFROMX| | | | |
Predicate Information (identified by operation id):
---------------------------------------------------
3 - filter(SYS_CHECKACL("ACLOID","OWNERID",xmltype('...

你大概对为上述查询生成的执行安排并不餍足。尤其是,所拍卖的行数恐怕尤其大。由于
SQL
调整的主要性目的是防止访问对结果没有别的影响的行,由此恐怕要连续调整查询以优化质量。对查询中蕴涵的
XPath 表明式举行再一次建立模型后,能够重新重试它,如下所示:

SELECT count(*)
FROM oe.purchaseorder, XMLTable(
'for $i in /PurchaseOrder
where $i/User = "CJOHNSON"
return $i/User'
PASSING OBJECT_VALUE) ptab;
这次,输出应如下所示: 
COUNT(*)
----------
9
Execution Plan
---------------------------------------------------
Plan hash value: 3411896580
---------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
----------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 29 | 7 (0) | 00:00:01 |
| 1 | SORT AGGREGATE | | 1 | 29 | | |
| 2 | NESTED LOOPS | | 1 | 29 | 7 (0) | 00:00:01 |
| 3 | FAST DUAL | | 1 | | 2 (0) | 00:00:01 |
|* 4 | TABLE ACCESS FULL | PURCHASEORDER | 1 | 29 | 5 (0) | 00:00:01 |
Predicate Information (identified by operation id):
---------------------------------------------------
4 - filter("PURCHASEORDER"."SYS_NC00022$"='CJOHNSON' AND
SYS_CHECKACL("ACLOID","OWNERID",xmltype('...

您能够看来,以上显示的询问生成相同的末段结出,但它们的实践安顿并分歧。查看最终一个示范中的
XQuery 表达式,您大概会注意到它迭代顶层 PurchaseOrder 元素,个中的各个PurchaseOrder 成分都代表依据 PurchaseOrder XMLType
情势的表中的一条龙。那代表实际上海重机厂写 XQuery
表明式,以迭带基础对象表(用于存款和储蓄分解的 PurchaseOrder
文书档案)中的行。与查询要迭代不表示基础表中的单个行的 XML
成分相比较,该措施的本性更好一些。

但在一些情状下,很难发现 XQuery
表达式的哪位构造将使一些查询的性质更好。那就是为啥最幸好开发阶段使用调整工具的因由。

将动态变量绑定到 XQuery 表明式

另一种能够显著坚实 XQuery
表达式执行品质的技巧是运用绑定动态变量。使用绑定变量(而不是将变量串联为字符串)能够使
Oracle 重用 SQL 语句,从而裁减分析开支并分明抓好应用程序的性质。能够在
XMLQuery 和 XMLTable SQL 函数中动用 PASSING 子句将动态变量绑定到 XQuery
表明式。该技能使你能够依据客户端代码中计算的参数动态生成 XML。列表 3
中的示例演示了怎么样在从 PHP 脚本执行的 XQuery 查询中利用绑定变量。

列表 3:使用绑定变量

//File:BindVars.php
$user = 'hr';
$pswd = 'hr';
$db ='(DESCRIPTION=
(ADDRESS_LIST=
(ADDRESS=(PROTOCOL=TCP)(HOST=localhost)(PORT=1521))
)
(CONNECT_DATA=(SID=orclR2)(SERVER=DEDICATED))
)';
$empno=100;
$conn = oci_connect($user, $pswd, $db);
$sql = 'SELECT XMLQuery('."'".'for $i in ora:view("employees")/ROW
where $i/EMPLOYEE_ID = $empno
return (
{$i/EMPLOYEE_ID,
$i/EMAIL,
$i/JOB_ID}
)'."'".'PASSING XMLElement("empno", :empno) AS "empno"
RETURNING CONTENT).GetStringVal() AS RESULT FROM DUAL';
$query = oci_parse($conn, $sql);
oci_bind_by_name($query, ":empno", $empno, 3);
oci_execute($query);
oci_fetch($query);
$str = oci_result($query, 'RESULT');
print $str;
?>

列表 3 中显得的脚本应生成以下输出(注意,浏览器中恐怕不会议及展览示标记):

100
SKING
AD_PRES

XQuery 与 XSLT

即使 Oracle 在 Oracle XML DB 中提供了二个自带 XSLT
处理器,但在众多状态下(尤其是在拍卖大型文书档案时),XQuery 对于创设 XML
更迅捷。其它,XQuery 表达式日常比为同一作业设计的 XSLT
样式表更具可读性,并且更掌握。与 XSLT 一样,XQuery 不但可用来将一个 XML
文书档案转换为另八个 XML 文书档案,而且还可用于将 XML
转换为另一种基于文本的格式,如 HTML 或 WML。

在本文后边的查询 XMLType 数据部分中,您看到了三个有关使用 XQuery 将3个XML 文书档案转换为另一个 XML 文书档案的言传身教。具体而言,该示例使用 XQuery
表明式总结示例数据库方式 OE 的 purchaseorder
表中储存的订单的订单一共,然后为处理的每一种订单生成了3个 OrderTotal XML
成分。实际上,您能够动用 XSLT
执行同一操作。为此,您首先须要创立二个用到于 PurchaseOrder XML 文书档案的
XSLT 样式表,以浮动对应的 OrderTotal 成分。对于此示例,能够应用列表 4
中所示的 XSLT 样式表。

列表 4:使用 XSLT 计算小计总和 (Quantity * UnitPrice)

http://www.w3.org/1999/XSL/Transform" version="1.0">



























为方便起见,您只怕须求将此 XSL
样式表保存在数据库中,然后再起来选用它。例如,您可以将样式表作为文件能源保存在
Oracle XML DB
新闻库中。执行该操作的办法之一是将样式表作为文件保留到本三步跳件系统中,然后使用以下某些网络球组织议将它移动到
XML 音信库:FTP、HTTP 或 WebDAV。倘若你已经将列表 4 中的 XSLT 样式表作为
orderTotal.xsl 保存在 /public
音信库文件夹中,未来能够按以下示例所示将它用作 XMLTransform SQL
函数的参数(假如你以 OE/OE 的地位登录):

SELECT XMLTRANSFORM(OBJECT_VALUE,
xdbUriType('/public/orderTotal.xsl').getXML()).GetStringVal() AS RESULT FROM
purchaseorder WHERE existsNode(OBJECT_VALUE, 
'/PurchaseOrder[User = "EABEL"]') = 1;

上述查询将拍卖用户 EABEL 请求的具有订单(即存款和储蓄在 XMLType 的暗中同意PurchaseOrder 表中的订单)并将扭转与查询 XMLType 数据部分中的 XQuery
查询同一的出口。

将列表 4 中的 orderTotal XSLT 样式表与查询 XMLType
数据部分中的示例使用的 XQuery 表明式进行比较,您或然会注意到,XQuery
方法要比 XSLT 方法更具吸重力。至少在应用 XQuery
时,您只需编写很少的代码即可获得同等的尾声结出。

查询 卡宴SS 信息提供

是因为 RSS 音讯提供精神上是3个托管的 XML 文件(昂科拉SS
音信阅读器从中获得头条音信或此外剧情),由此得以像处理其他其他可以透过
Web 获得的 XML
文书档案那样来处理它。正如您在本文前面包车型客车查询外部数据源部分中所见,能够应用
XQuery 查询任何能够经过 UGL450L 访问的 XML。您通过 XMLTable 和 XMLQuery SQL
函数中的 PASSING 子句动态绑定全数外部 XML 数据源。以下是三个查询 SportageSS
消息提供的 XQuery 示例:

SELECT XMLQuery(
'for $i in $h//channel
return;

{$i/lastBuildDate}

{for $j in $h//item
where ora:contains($j, "PHP")
return  {($j/title, $j/link)}}

'
PASSING xmlparse (document httpuritype
('http://www.oracle.com/technology/syndication/rss_otn_news.xml').getCLOB()) as "h"
RETURNING CONTENT).getStringVal() as RESULT FROM DUAL;

该 XQuery 应生成二个 XML 文书档案,在那之中富含 Oracle 技术网 (OTN) 近年来表露的与
PHP 技术有关的头条音信列表。所生成的 XML 文书档案只怕如下所示:

Tue, 01 Nov 2005 19:37:42 GMT


http://www.oracle.com/technology/xe


http://www.oracle.com/technology/pub/articles/oracle_php_cookbook


http://www.oracle.com/technology/tech/php/zendcore/index.html

但在开发实际应用程序时,您将很大概必要 XQuery 表明式直接生成 HTML
标记,而不是只是转移一个如上所示的 XML
文书档案。那样,您便能够构建二个更灵敏、可维护性更高的应用程序,原因是在那种情状下,全体PAJEROSS 处理(从提取需要的多寡到将它包裹在 HTML
标记中)都将更换到数据库。这使你不用编写负责 帕杰罗SS
处理的应用程序代码。实际上那意味你不用在比如 CRUISERSS
信息提供的结构已经变更的地方下修改应用程序代码。相反,您只需修改用于 库罗德SS
处理的 XQuery 表达式。

总结

你已经在本文领悟到,XQuery
是1个总结的询问语言,它提供了一种用于查询、营造和转换 XML
数据的长足方法。就算 Oracle XQuery 实施使你能够操作任何能够用 XML
表示的多少(无论它存储在数据库中、位于网站上只怕存储在文件系统中),但将拍卖的数据移动到数据库中始终是一个正确的主意。对于数据库中储存的数目,Oracle
XML DB(对 XPath
重写使用同一机制)只可以眼看优化处理那个基于以下数据创设的 XQuery
表达式:那一个多少包含关全面据、对象-关周密据或利用结构化(对象-关系)存款和储蓄技术存款和储蓄的依照XML 情势的 XMLType 数据。

(责编:铭铭)

原文:Oracle
XQuery查询、构建和转换XML

重返数据库首页

相关文章