ORACLE, 你把空字串怎麼了?

腦海中一直存著清晰的一幕,牙牙學語摸索SQL語法的青澀少年Jeffrey,端坐SQL大師Ryan的跟前,聽著諄諄教誨:

孩子,閉上眼晴,用原力去感受... 在SQL世界裡NULL具有獨特的魔力,VARCHAR欄位儲存著NULL或是空字串? 在意義上是絕對不同的...

後來在DB、Web領域打滾多年,我常常採行這項Schema設計理念:NULL代表使用者未曾輸入過任何資料,空字串則代表使用者輸入了,但未指定任何值。在SQL Server的世界裡,這條鐵律一直運行得很好,直到我遇到了ORACLE...

今天在寫一個動態的SQL複合條件查詢,為了簡化起見,用了以下的技巧:

SELECT SomeColumns....
FROM SomeTable
WHERE (:userId = '' OR UserIdCol = :userId)
AND SomeOtherCriteria...

我打的如意算盤是,如果userId傳入空字串,就不限定UserIdCol的值;否則就透過指定userId的方式,只傳回UserIdCol=:userId的結果。

 

測試了一下,將:userId參數設為空字串,理應列出所有的資料。很好!! 什麼都沒傳回來... orz

Debug了一下,才發現在ORACLE裡,根本沒有空字串這種東西,空字串會被視為NULL。因此,'' = ''等同於NULL = NULL,等於比對不會傳回True或False,而是傳回NULL。

接著,用Google找到相關說明。雖然違背了ANSI SQL 92的定義,但ORACLE的確會將空字串當作NULL處理,導致了非我預期的結果。

由於不能因為這點特性要求更換DataBase,山不轉路轉,路不轉人轉,上述的SQL語法要改寫成:

SELECT SomeColumns....
FROM SomeTable
WHERE (:userId IS NULL OR UserIdCol = :userId)
AND SomeOtherCriteria...

繼續幹活去!

Published 01 April 2008 03:20 PM 由 Jeffrey
Filed under:


意見

# ryan said on 03 April, 2008 12:41 PM

孩子, 對Oracle的怨恨或是orz, 只會引領你投入黑暗的勢力. 不過....既然你已經自封為Darkthread黑武士, 也就沒什麼關係, 反正你兒女會把宇宙帶回合諧的原力世界, 該罵的還是盡量罵吧.

May Force with You!

你的看法呢?

(必要的) 
(必要的) 
(選擇性的)
(必要的) 

請輸入以上的數字:

搜尋

Go

<April 2008>
SunMonTueWedThuFriSat
303112345
6789101112
13141516171819
20212223242526
27282930123
45678910
 
RSS
【工商服務】

Tags 分類檢視
關於作者

一個醉心技術又酷愛分享的Coding魔人,十年的IT職場生涯,寫過系統、管過專案, 也帶過團隊,最後還是無怨無悔地選擇了技術鑽研這條路,近年來則以做一個"有為的中年人"自許。

文章典藏
其他功能

這個部落格


BlogLook Score and Rank

Syndication