MySQL 5.1 提供XML內置支持(XPath)
前些天說到了MySQL5提供了內置的XML文件解析和修改函數,今天找了點MySQL網站上的資料和例子,翻譯了一下,希望能給使用數據庫存儲XML和XSLT的同志一些幫助。
MySQL 5.1.5版本中添加了對XML文檔進行查詢和修改的函數,分別是ExtractValue()和UpdateXML(),下面是這兩個函數的使用示例:
還是一樣我們首先建立一個示例數據庫,然后將范例中使用的XML文檔輸入到數據庫中:
CREATE TABLE x (doc VARCHAR(150));
INSERT INTO x VALUES
('
<book>
<title>A guide to the SQL standard</title>
<author>
<initial>CJ</initial>
<surname>Date</surname>
</author>
</book>
');
INSERT INTO x VALUES
('
<book>
<title>SQL:1999</title>
<author>
<initial>J</initial>
<surname>Melton</surname>
</author>
</book>
');
大家可以看到,doc列的內容中包含了自己的層次結構,以XML格式體現包含書名和作者的書本,其中作者還包含名字簡寫大寫以及姓。這是流行的排版和儲存格式,字母"<book>" 和</book>"是標記,使用戶更容易理解內部的層次結構。
下面先看看ExtractValue()的用法吧
語法:
EXTRACTVALUE (XML_document, XPath_string);
第一個參數:XML_document是String格式,為XML文檔對象的名稱,文中為Doc
第二個參數:XPath_string (Xpath格式的字符串) ,如果不了解Xpath語法,可以在網上查找教程。
作用:從目標XML中返回包含所查詢值的字符串
示例#E1:
mysql> SELECT EXTRACTVALUE(doc,'/book/author/initial') FROM x;
+------------------------------------------+
| EXTRACTVALUE(doc,'/book/author/initial') |
+------------------------------------------+
| CJ |
| J |
+------------------------------------------+
2 rows in set (0.01 sec)
可以看到,EXTRACTVALUE()函數將/book/author/initial節點中的值取出來,并通過Select返回。因此需要簡單的查找XML文檔中的值,只要在XPath_string參數中指定好層次和節點就行了。
示例#E2
mysql> SELECT EXTRACTVALUE(doc,'/*/*/initial') FROM x;
+----------------------------------+
| EXTRACTVALUE(doc,'/*/*/initial') |
+----------------------------------+
| CJ |
| J |
+----------------------------------+
2 rows in set (0.01 sec)
如果查詢前并不知道層次關系,你也可以使用通配符進行層次的匹配,不過當XML文檔比較大的時候查找速度會很慢滴。
示例#E3
mysql> SELECT extractValue(doc,'/book/child::*') FROM x;
+---------------------------------------------+
| extractValue(doc,'/book/child::*') |
+---------------------------------------------+
| A guide to the SQL standard |
| SQL:1999 |
+---------------------------------------------+
2 rows in set (0.00 sec)
使用/book/child::語句我們可以找到Book節點下的首個節點,文中是title。除了child以外,我們還有其他的參數:
child ... 指定節點的下一子節點)
descendant ... 節點下包含的所有層次中的數據
parent ... 指定節點的上一節點
ancestor ... 節點以上所有層次的數據
following-sibling ... 同一層次的下一個節點
preceding-sibling ... 同一層次的上一個節點
self ... 自身
示例#E4
mysql> select
extractValue(doc,'/book/author/surname[self:text()="Date"]') from x;
+--------------------------------------------------------------+
| extractValue(doc,'/book/author/surname[self:text()="Date"]') |
+--------------------------------------------------------------+
| Date |
| |
+--------------------------------------------------------------+
2 rows in set (0.00 sec)
這里是一個使用條件表達式進行數據查找的例子,具體就不解釋了,都是符合Xpath語法的,大家可以參考一下Xpath表達式的用法。
雖然上面的extractValue()函數都使用在SELECT列表中,其實該函數是可以使用在任何一個允許使用表達式的語句中的。
這里提示一點,使用這個函數可以輕松將XML文檔列與全文檢索結合起來。
來到UpdateXML()函數了
語法
UPDATEXML (XML_document, XPath_string, new_value);
第一個參數:XML_document是String格式,為XML文檔對象的名稱,文中為Doc
第二個參數:XPath_string (Xpath格式的字符串) ,如果不了解Xpath語法,可以在網上查找教程。
第三個參數:new_value,String格式,替換查找到的符合條件的數據
作用:改變文檔中符合條件的節點的值
示例#U1
mysql> select UpdateXML(doc,'/book/author/initial','!!') from x;
+----------------------------------------------------------+
| UpdateXML(doc,'/book/author/initial','!!') |
+----------------------------------------------------------+
|
<book>
<title>A guide to the SQL standard</title>
<author>
!!
<surname>Date</surname>
</author>
</book> |
|
<book>
<title>SQL:1999</title>
<author>
!!
<surname>Melton</surname>
</author>
</book> |
+----------------------------------------------------------+
2 rows in set (0.00 sec)
UpdateXML函數的前兩個參數用法以及寫法與ExtractValue是一樣的,因為這里需要查找到符合條件的數據節點。第三個參數就是為了替換節點字符串的。文中我們就使用!!字符串替換了book/author/initial節點的值。返回值是整個改變后的XML文檔。這里記住,由于我們使用的是Select語句,因此并沒有對真正的數據進行修改,而是在內存中將取出的數據進行修改然后返回給用戶。如果需要徹底的修改文檔內容,可以使用下面語句:
UPDATE x SET doc = UpdateXML(doc,/book/author/initial','!!');
細心的人也許發現這里有一個錯誤,也許是Bug,因為我們并不想修改結構化的文檔,而僅僅需要修改內容,但UpdateXML函數將<initial>CJ></initial>整個文本改成了!!,這樣就不是我們所想要的了,因為它改變了整個文檔結構。因此如果你需要的僅僅是修改這個結構化文檔的內容部分,而不是整個文本,可以使用:
UpdateXML(doc,'/book/author/initial','<initial>!!</initial>') from x;
示例#U2
mysql> select
extractvalue(
UpdateXML(doc,'/book/author/initial','<initial>!!</initial>'),'/book/author/
initial') from x;
+---------------------------------------------------------------------------
--------------------------+
|
extractvalue(
UpdateXML(doc,'/book/author/initial','<initial>!!</initial>'),'/book/author/
initial') |
+---------------------------------------------------------------------------
--------------------------+
| !!
|
| !!
|
+---------------------------------------------------------------------------
--------------------------+
2 rows in set (0.01 sec)
最后一個例子,ExtractValue()函數和UpdateXML()函數的嵌套使用,結果是給我們展示將initial節點的值改成!!后選擇查詢initial節點的內容,結果大家也能看到了。
上面只是這兩個函數的最基本用法,如果大家還需要更多的資料,或有一些自己的心得,歡迎一起討論。
MySQL 5.1.5版本中添加了對XML文檔進行查詢和修改的函數,分別是ExtractValue()和UpdateXML(),下面是這兩個函數的使用示例:
還是一樣我們首先建立一個示例數據庫,然后將范例中使用的XML文檔輸入到數據庫中:
CREATE TABLE x (doc VARCHAR(150));
INSERT INTO x VALUES
('
<book>
<title>A guide to the SQL standard</title>
<author>
<initial>CJ</initial>
<surname>Date</surname>
</author>
</book>
');
INSERT INTO x VALUES
('
<book>
<title>SQL:1999</title>
<author>
<initial>J</initial>
<surname>Melton</surname>
</author>
</book>
');
大家可以看到,doc列的內容中包含了自己的層次結構,以XML格式體現包含書名和作者的書本,其中作者還包含名字簡寫大寫以及姓。這是流行的排版和儲存格式,字母"<book>" 和</book>"是標記,使用戶更容易理解內部的層次結構。
下面先看看ExtractValue()的用法吧
語法:
EXTRACTVALUE (XML_document, XPath_string);
第一個參數:XML_document是String格式,為XML文檔對象的名稱,文中為Doc
第二個參數:XPath_string (Xpath格式的字符串) ,如果不了解Xpath語法,可以在網上查找教程。
作用:從目標XML中返回包含所查詢值的字符串
示例#E1:
mysql> SELECT EXTRACTVALUE(doc,'/book/author/initial') FROM x;
+------------------------------------------+
| EXTRACTVALUE(doc,'/book/author/initial') |
+------------------------------------------+
| CJ |
| J |
+------------------------------------------+
2 rows in set (0.01 sec)
可以看到,EXTRACTVALUE()函數將/book/author/initial節點中的值取出來,并通過Select返回。因此需要簡單的查找XML文檔中的值,只要在XPath_string參數中指定好層次和節點就行了。
示例#E2
mysql> SELECT EXTRACTVALUE(doc,'/*/*/initial') FROM x;
+----------------------------------+
| EXTRACTVALUE(doc,'/*/*/initial') |
+----------------------------------+
| CJ |
| J |
+----------------------------------+
2 rows in set (0.01 sec)
如果查詢前并不知道層次關系,你也可以使用通配符進行層次的匹配,不過當XML文檔比較大的時候查找速度會很慢滴。
示例#E3
mysql> SELECT extractValue(doc,'/book/child::*') FROM x;
+---------------------------------------------+
| extractValue(doc,'/book/child::*') |
+---------------------------------------------+
| A guide to the SQL standard |
| SQL:1999 |
+---------------------------------------------+
2 rows in set (0.00 sec)
使用/book/child::語句我們可以找到Book節點下的首個節點,文中是title。除了child以外,我們還有其他的參數:
child ... 指定節點的下一子節點)
descendant ... 節點下包含的所有層次中的數據
parent ... 指定節點的上一節點
ancestor ... 節點以上所有層次的數據
following-sibling ... 同一層次的下一個節點
preceding-sibling ... 同一層次的上一個節點
self ... 自身
示例#E4
mysql> select
extractValue(doc,'/book/author/surname[self:text()="Date"]') from x;
+--------------------------------------------------------------+
| extractValue(doc,'/book/author/surname[self:text()="Date"]') |
+--------------------------------------------------------------+
| Date |
| |
+--------------------------------------------------------------+
2 rows in set (0.00 sec)
這里是一個使用條件表達式進行數據查找的例子,具體就不解釋了,都是符合Xpath語法的,大家可以參考一下Xpath表達式的用法。
雖然上面的extractValue()函數都使用在SELECT列表中,其實該函數是可以使用在任何一個允許使用表達式的語句中的。
這里提示一點,使用這個函數可以輕松將XML文檔列與全文檢索結合起來。
來到UpdateXML()函數了
語法
UPDATEXML (XML_document, XPath_string, new_value);
第一個參數:XML_document是String格式,為XML文檔對象的名稱,文中為Doc
第二個參數:XPath_string (Xpath格式的字符串) ,如果不了解Xpath語法,可以在網上查找教程。
第三個參數:new_value,String格式,替換查找到的符合條件的數據
作用:改變文檔中符合條件的節點的值
示例#U1
mysql> select UpdateXML(doc,'/book/author/initial','!!') from x;
+----------------------------------------------------------+
| UpdateXML(doc,'/book/author/initial','!!') |
+----------------------------------------------------------+
|
<book>
<title>A guide to the SQL standard</title>
<author>
!!
<surname>Date</surname>
</author>
</book> |
|
<book>
<title>SQL:1999</title>
<author>
!!
<surname>Melton</surname>
</author>
</book> |
+----------------------------------------------------------+
2 rows in set (0.00 sec)
UpdateXML函數的前兩個參數用法以及寫法與ExtractValue是一樣的,因為這里需要查找到符合條件的數據節點。第三個參數就是為了替換節點字符串的。文中我們就使用!!字符串替換了book/author/initial節點的值。返回值是整個改變后的XML文檔。這里記住,由于我們使用的是Select語句,因此并沒有對真正的數據進行修改,而是在內存中將取出的數據進行修改然后返回給用戶。如果需要徹底的修改文檔內容,可以使用下面語句:
UPDATE x SET doc = UpdateXML(doc,/book/author/initial','!!');
細心的人也許發現這里有一個錯誤,也許是Bug,因為我們并不想修改結構化的文檔,而僅僅需要修改內容,但UpdateXML函數將<initial>CJ></initial>整個文本改成了!!,這樣就不是我們所想要的了,因為它改變了整個文檔結構。因此如果你需要的僅僅是修改這個結構化文檔的內容部分,而不是整個文本,可以使用:
UpdateXML(doc,'/book/author/initial','<initial>!!</initial>') from x;
示例#U2
mysql> select
extractvalue(
UpdateXML(doc,'/book/author/initial','<initial>!!</initial>'),'/book/author/
initial') from x;
+---------------------------------------------------------------------------
--------------------------+
|
extractvalue(
UpdateXML(doc,'/book/author/initial','<initial>!!</initial>'),'/book/author/
initial') |
+---------------------------------------------------------------------------
--------------------------+
| !!
|
| !!
|
+---------------------------------------------------------------------------
--------------------------+
2 rows in set (0.01 sec)
最后一個例子,ExtractValue()函數和UpdateXML()函數的嵌套使用,結果是給我們展示將initial節點的值改成!!后選擇查詢initial節點的內容,結果大家也能看到了。
上面只是這兩個函數的最基本用法,如果大家還需要更多的資料,或有一些自己的心得,歡迎一起討論。
posted on 2006-07-11 00:12 benchensz 閱讀(10952) 評論(9) 編輯 收藏 所屬分類: 隨便寫寫(比較有用,值得看看)