2010年10月4日 星期一

xml,schema,document,sax,dom

xml:
*w3c標準
*是SGML簡化
*比HTML困難
*目前主流之訊息文件交換標準:目前各程式元件間(尤其是網路元件)以訊息溝通時的主流交換元件.
舉例來說:網路購物時,A程式是瀏覽清單模組(以java開發),B程式是結帳模組(以.net開發),
彼此之間可以書單(書單.xml)來溝通,而不會有問題
*跨平台:因此,跨作業平台,跨語言,跨開發環境,也是他的重要優點,也是流行起來的原因
*較HTML嚴謹
*標準化,結構化

舉例來說:
假設在購物車買了一本書,
書名(title)叫做Everyday Italian,
作者(author)是Giada De Laurentiis,
出版年份(year)是2005,
價格(price)是30.00美元
就要結帳...

用人的思考去想,
書單的結構會是長怎樣?
書單裡面會有很多書
書又有各種屬性,可以表示成下列這樣的結構:

書單
-書 -書名(title):Everyday Italian,
-作者(author):Giada De Laurentiis,
-出版年份(year):2005,
-價格(price):30.00美元

很想你用一個表格去列出所有的書
可是你怎麼在一個文字檔顯示表格?
因此就衍伸用一些tag(標籤)來表示
比如說上面的結構變成這樣:









是不是蠻直覺的?
例如每一本書就用來表示
裡面包的是這本書的各種屬性
值得注意的是每一個tag都應該要有配對
也就是要有頭有尾:
"" ""
頭 尾
這點跟html有很大的不同
html可以允許沒有尾巴(可以讀html的軟體還是可以讀)
但是xml就不行了,一定要為"有頭有尾"的"標準","完整"結構
這樣有標準、完整結構的特點也是xml受歡迎的原因之一

上述的書單如果加上標頭的xml版本宣告就變成正式的xml文件(xml document)了
書單(books.xml)應為:
第一行就是xml宣告了!(xml version什麼的那行)
而第二行是註解(edited by xmlspy的那行)

以上就是xml document了

xml schema:
*驗證xml document所需的規則文件

由來:
其實xml很free,只要你有配對,
標籤是什麼,裡面要長怎麼樣都可以自訂
不過這樣一來就會有一個問題
那麼程式要如何來解析你自訂的xml文件呢?
不會是自己要寫程式來解析吧?
試想想?你要讀進一個文字檔,然後還要比對字串是不是book開頭的
是不是太累了?
這種東西當然會有自動程式,也就是所謂的xml parser幫你做
你餵給他一個xml文件 丟到xml parser之後 就會出來一個可能是樹狀架構的一個物件
看到這邊 常寫物件導向程式語言(java,c++...etc)的人應該就能了解
這種自動化存在的意義了吧?
把xml文件轉成物件之後 當然就非常好操作啦!
可是問題就來了...既然可以自訂規則...你是不是要把你自訂的規則,標籤的定義,
裡面可以裝什麼屬性,他的值是字串,還是數字,是不是通通要告訴xml parser,
要叫人家幫你辨識,你總要告訴他規則吧?
這就是xml schema的存在意義了
其實可以做這種事情的也不是只有xml schema而已
還有一種叫做DTD的也可以~但我沒有要介紹
因為DTD比較麻煩 而且也比xml schema規矩較多
慢慢的也不被人常用了

在這裡整理一下:
驗證xml文件的規則文件:
1.xml schema
2.DTD

接下來就是要來介紹怎麼寫xml schema了
規則很多很多...這邊只濃縮簡單介紹
讓大家有個基本概念
舉剛剛上面的例子:
這個的xml schema怎麼寫?(也就是規則有啥?)
大家可以看到有:
*bookstore標籤:裡面可以包book標籤
*book標籤:
1.有category屬性:屬性值是string
2.title標籤:
a.有lang屬性:屬性值是string
b.理面的值是string
3.author標籤:裡面的值是string
4.year標籤:裡面的值是數字integer
5.price標籤:裡面的值是小數decimal
接下來我們直接看寫好的xml schema:
有一些東西應該就不難了解了
xs:element對應到的就是每個標籤
name裡面的值就是他將來在標籤的名字
type裡面可以指定是xs:string(字串)或是xs:decimal(小數)之類的
如果一個標籤裏面(大擴號小擴號中間)需要夾別的東西(我們稱為屬性attribute)
就需要用xs:attribute來定義
至於xs:complexType(複合型態)
指的是當你一個標籤裏面不只有你一個標籤(像是book,bookstore這種標籤)
你就要使用這個標籤把你每個標籤可以包的東西給包起來
這樣xml parser才會知道你的book標籤裏面可以包的東西
哪裡是頭,哪裡是尾,可以包什麼阿!
xs:sequence指的是接下來的標籤是有順序的
那一剛開始xs:schema指的是xml schema的剛開頭
裡面的標籤囉哩巴縮的都是固定的用語喔!不能亂刪

接下來我們再來看如果需要用這個xml schema的xml document
應該要怎麼寫?
你會說阿怎麼突然間多了一大串在bookstore那裡?
不是剛剛那個文件就可以了嗎?
沒錯!因為你要用這個xml schema來解析這個文件
所以你當然要告訴他你的xml schema叫什麼吧?
舉例來說 我們的schema檔名就叫做:books.xsd
所以你可以在bookstore那個標籤的最後那裏看到books.xsd
這就是在告訴parser你等下要用的規則就是要用這個檔案的~

(補充:各位我知道有些人會跟我說不是叫做檔案
應該是一些命名規則,但這邊為了簡略說明,我就直接講檔案意思比較清楚
如果連命名規則都要講進去...會很亂Xd)

最後來跟大家講一下對應的dom:
這張就是剛剛那個xml document所對應的dom
有一些程式慧根的人應該對應上面的xml document,xml schema
看一下就知道在幹麻了
相信下面也可以省略不看了XD

剛剛有講到xml parser可以解析出一個"樹狀架構的物件"~這個就是dom
用圖形來描述的話就是像上面這樣
再對應xml schema文件xsd來看的話就可以非常清楚了
bookstore是父節點(parent),子節點(child)是book
對應到xml document就是巢狀架構
book標籤有attribute category
底下還有標籤(element)title,author,year,price
以下類推不講了,
值得注意的是那個siblings就是指兄弟節點的意思

在這邊另外提到xml parser
並不是只有一種可以解析出dom的方式
還有另一種方式為循序檔讀取的方式(sax)
講一下dom跟sax是什麼鬼,有什麼差異
我們知道一種方式會解析出dom了,
他就是會把xml文件一次解析出一顆大樹(dom)
但是試想一種狀況,假設你只是想要知道xml文件的某一個欄位值是什麼
比如說:這一本書的價格是多少錢
你也要每次都解析出搞一顆"大樹"出來,只是為了想查某一個"小值"嗎?
因此有另外一種方法,是循序讀取的方式,也就是sax
幫你只查那一個值
最後整理一下:
xml解析的方式有兩種:
1.dom
2.sax

以上,收工
有什麼問題再說,我會盡量解釋