Merge語法在一開始的規劃上,主要是為了可以在一次的SQL執行中,完成新增與修改資料的動作,避免兩次的Full Table Scan對資料庫效能造成的影響。這樣的做法也讓程式設計師與資料庫管理者,可以更巧妙地利用SQL語法,滿足商業邏輯上的需求,因此Oracle資料庫在版本10g的時候,更強化Merge的語法結構,讓它可以有更靈活的應用。主要的新特性有下列三點:
●新增(Insert)與修改(Update)可只擇其一。
●Where子句的使用。
●Delete子句的使用。
新增與修改可只擇其一
在Oracle 9i的版本中,Merge語法「WHEN MATCHED THEN UPATE SET……」與「WHEN NOT MATCHED THEN INSET……」兩個子句是必須同時存在,缺一不可的。不過,在Oracle 10g的時候,這兩個子句只要其中一個出現在Merge語法中就可以了,舉例如圖一。
圖一的結果可知,由於Merge語法中只有「WHEN NOT MATCHED THEN INSERT」的子句,而沒有「WHEN MATCHED THEN UPDATE SET」的子句,因此,我們可以看到CUS_ID為3的資料欄位,已被新增到目標資料表;而目標資料表中CUS_ID為2的資料並沒有被修改。
在Merge語法的使用上,並不是針對一般在SQL語法上撰寫的應用。在一般的應用上,直接用圖二的寫法,就可以達到只有新增或只有修改的目的。
而是特別針對在程式撰寫的過程中,如果在系統的規劃上是可以有「只有新增」、「只有修改」、或「同時新增與修改」這三種選擇時,我們可以把一個完整的Merge語句分解成「MERGE……」、「WHEN MATCHED……」、以及「WHEN NOT MATCHED……」三個部份,並再利用選擇條件(例如:if),依據使用者的選擇組合Merge語法,組合出「WHEN MATCHED……」及「WHEN NOT MATCHED……」子句都有的SQL 語法,還是兩者間只有一個存在的SQL 語法,以提供使用者靈活的運作。
Where子句的使用
Oracle 9i時,Merge語法中的Insert與Update子句後面,並不允許有Where條件子句出現。因此在有資料表融合(Merge)的過程中,如果有Where條件子句的需求時,我們一般會在USING子句,搭配子查詢(Sub-query)解決這樣的問題。
例如PRODUCT_TABLE_SALE是業務部門中的產品資料表,而PRODUCT_TABLE_PM是產品管理部門的產品資料表,由於該公司每個月月初,會依產品管理部所定義的產品訂價(Price)與內容說明(Desc)修正業務部門產品資料表中的資訊。
但對於產品狀態(STATUS)為不使用(UNUSE的資料,其實已經不用再轉入業務部門的產品資料表,對於業務部門的同仁而言,他們其實只需要知道還有在使用中、可以賣的產品)。
為了因應這樣的需求,Oracle 10g允許Merge語法中的Insert以及Update子句擁有 Where的條件,讓資料表的融合(Merge)是更可以有選擇性的。
述上例,該公司基於I/O效能的考量,所以在Update子句下,並不是所有沒有在使用的產品(product_status <> 'UNUSE')都對銷售部門的產品資料表(product_table_sale)進行更新,我們只針對有新的發展(new_develop='YES')的資料記錄修改。
在Oracle 10g,如圖三,我們可以各別在Insert與Update的子句中,利用Where子句中來設定的不同的條件子句(pr.product_status <> 'UNUSE' 以及 pr.product_status <> 'UNUSE' and pr.new_develop= 'YES'),以過濾不需要被融合的資料。
Delete子句的使用
Merge語法在設計的最初,是針對資料儲倉的需求,因此「只進不出」的資料儲倉特性,使Oracle 9i在規劃Merge語法時,並沒有將目標資料表中,刪除資料的特性納入考量。
不過,隨著商業邏輯應用的靈活化,Merge語法並不只單單應用在資料倉儲的環境,因此,同樣是系統效能的考量,Oracle 10g的版本,即將有可能造成Full Table Scan的Delete子句,納入整個Merge語法的架構中,以滿足更多的商業邏輯上的需求。
再續上述的例子,由於業務部門的產品資料表,有可能存放了產品管理部門已經不再使用的產品(STATUS為UNUSE)。對於這些產品資訊,理論上,我們應該將它從業務部門的產品資料表中刪除,所以Merge語法修改如下圖四。
更靈活的SQL撰寫方法
Merge語法是Oracle在9i時,是為了資料倉儲的需求下的資料表融合所設計的新語法,藉由Full Table Scan的減少,提升SQL的執行效能。
這樣的新語法,在商業邏輯的應用上,恰好提供資料庫管理師及程式設計師更靈活的SQL撰寫方法。為了更強化Oracle SQL語法的撰寫,Oracle更在10g時,特別針對這個語法,規劃更完善的結構。
因此從資料庫設計的角度來看,對於使用Oracle 10g的企業,重新思考整個資料庫規劃與程式撰寫,以強化系統的建置。
作者/杜奕鋒
艾群科技技術顧問,崑山大學講師。國立中央大學畢業,專精於商業流程設計、資料庫管理、T-SQL 及軟體整合。通過 OCP(8i/9i/10g)、RHCE、SCSA、SCNA、SCJP 等認證。
曾任職於 104 人力銀行,負責 eHRPortal 及 WorkFlow 系統整合;中華民國紡拓會,負責紡織業 ERP 系統導入;亦曾擔任臺灣護理學會系統導入顧問;並曾授課於關渡基督書院、永達技術學院。
圖一:Oracle 10g的Merge語法,允許只有「WHEN NOT MATCHED THEN INSERT」的子句,而沒有「WHEN MATCHED THEN Update SET」的子句。因此,我們可以看到CUS_ID為3的資料欄位,已被新增到目標資料表;而目標資料表中CUS_ID為2的資料並沒有被修改。
圖二:圖一的需求其實都可以不需要用到Merge即可達成,因為Merge並不是針對一般的應用而設計。
圖三:Oracle 9i時,Merge語法中的Insert與Update子句後面,並不允許有Where條件子句出現。但在Oracle 10g,我們可以利用Where子句過濾不需要被融合的資料。
圖四:隨著商業邏輯應用的靈活化,Merge語法並不只單單應用在資料倉儲的環境,因此, Oracle 10g即將有可能造成Full Table Scan的Delete子句,納入Merge語法的架構中,以滿足更多的商業邏輯上的需求。
熱門新聞
2025-01-13
2025-01-15
2025-01-14
2025-01-14
2025-01-13