結構化查詢語言-SQL
SQL-StructuredQueryLanguage是一種以「集合導向」的電腦語言,使用於關聯式數據庫的存取工作。「集合導向」是指它利用數學上集合的概念處理記錄。常用的概念有二:
併集(Union)
交集(Intersection)
SQL讀作
A集
B集
A集
B集
SQL也是一種「非程序性語言」(Non-procedurallanguage),即是它著重於「甚麼」(what)而非「怎樣」(how)。使用者只形容甚麼數據是需要的,而不是怎樣去得到數據。在電腦語言世代中,SQL屬於「第四代語言」(Fourthgenerationlanguage,4GL),數句語言便可完成大量工作。
基本上,SQL所能做到的,若使用Foxpro的數據庫指令如LISTFOR,REPLACE,CREATE,SETRELATION等也可做到;但學習SQL的重要性在於它是真正能夠跨越不同軟件及平台,在不同的數據庫平台甚至EXCEL上也可使用。SQL發源於大型電腦上伺服器數據庫語言上,但現在很多PC機及網頁語言(如VisualBASIC,Java,C++)也支援它了。
在伺服器/工作站(server/client)型式的網絡上,伺服器將內部資源分享給工作站,而工作站則向伺服器要求資源。有時候,一台工作站也可分擔存放數據庫工作,讓伺服器及其他工作站索取資料。
SQLnotes第一頁
VisualFoxpro提供一個「圖像使用者介面」(GraphiUserInterface,GUI)的工具,即QueryDesigner,容許使用者按動滑鼠便能寫作SQL。但我們也要懂得直接編寫SQL語句。
SELECT...FROM指令「查詢」query)就是從數據庫中索取符合條件(criteria)的信息的要求。查詢的結果是數據庫(中所有符合條件的記錄,以特定的次序排列起來。使用SELECT...FROM向電腦發出查詢前,我們不用開啟任何數據庫,只需設定數據庫所在的路徑,例如:
SETDEFAULTTOC:\SAMPLE1)SELECT*FROM
星號(*)的意思是全部欄。例如:
SELECT*FROMstudent
SQLnotes
第二頁
是要求Foxpro傳回所有在數據庫文件student內的記錄的全部欄,並按原來次序排列。
查詢的結果是一個以Query為名的暫存性「唯讀表格」(read-onlytable)。但當另一個新的查詢發出或離開Foxpro時,舊的結果便會消失。
SQL的SELECT和Foxpro的SELECT有很大分別,後者是用作選取工作區域!
2)SELECT,,...FROM
以特定欄名等代替星號,是只要部份欄的查詢。例如:SELECTreg_no,name_eFROMstudent
只會顯示兩個欄reg_no及name_e。
3)
SELECT...FROM...TOSCREENSELECT...FROM...TOPRINTERSELECT...FROM...TO
這三個查詢是分別將結果顯示於Foxpro顯示區,輸出至打印機及輸出至文本文件。
SQLnotes
第三頁
4)
SELECT...FROM...INTOTABLE
上面提及查詢的結果是暫存性及唯讀的,在離開Foxpro或發出新的查詢後便會消失。如果要保留結果成一個永久及可修改的數據庫表格,加入INTOTABLE
便可。
例如:
SELECTreg_no,
name_eFROM
student
INTOTABLEstuquery
新的永久表格stuquery便會存放著查詢的結果。
5)
SELECTDISTINCT
...
FROM
...
Distinct一字令查詢結果只顯示指定字段的不重覆項目。例如:
SELECTtitleFROMemployee
SELECTDISTINCTtitleFROMemployee
有四個SalesRepresentative
只有一個SalesRepresentative
而且,加上DISTINCT的查詢會自動以指定字段作升幕排序!
SQLnotes
第四頁
另外,如指定字段有兩個或以上,只有當所有字段相同只有排序的分別
時,記錄才被視為重覆。6)SELECT...FROM...ORDERBY...[ASC/DESC]
指定查詢結果以特定次序排列。
SELECT...FROM...ORDERBYemp_id
SELECT...FROM...ORDERBYtitleASC,last_nameDESC
SQLnotes
第五頁
ASC:即ascending升幕(預設方法)DESC:即descending降幕
先以title之升幕排序,相同的title中以last_name之降幕排序
7)
使用alias別名:
SELECT..AS..FROM..
查詢的字段名稱可使用AS來修改成較易明白的形式。
例如:(留意別名是不需使用引號''的)
SELECTemp_idASId,prod_nameASProduct_name,eng_nameASEnglish_nameFROMorders
甚至,AS是可以省略的,連中文名也可使用。
SELECTemp_idAS編號,prod_nameAS產品名稱,eng_nameAS英文名稱FROMorders
8)
在查詢中建立新字段利用AS,我們可以建立一些暫存字段,並使用函數計算結果。a)簡單四則運算
SQLnotes
第六頁
SELECTproduct_id,unit_price,quantity,unit_price*quantityAStotal_priceFROMorderitems
b)
預設函數ATAT(,)例如:傳回string1在string2出現的位置。
AT('DE','ABCDEF')的結果值是4。
SELECTsubstr(contact,1,AT('',contact)-1)ASnameFROMcustomer抽取空隔前的名字
c)
日期函數還記得下列以日期字段為對象的函數嗎?DAY(date1)MONTH(date1)YEAR(date1)以數字形式傳回date1的日子(例如:24)以數字形式傳回date1的月份(例如:9)以數字形式傳回date1的年份(例如:1999)以數字形式傳回date1的星期幾(例如:6)以文字形式傳回date1的星期幾(例如:Friday)
第七頁
CMONTH(date1)以文字形式傳回date1的日子(例如:September)DOW(date1)CDOW(date1)
[以上例子以1999年9月24日星期五為準]
SQLnotes
SELECTorder_date,day(order_date)ASDay,cdow(order_date)ASDay_Of_Week,cmonth(order_date)ASMonth,year(order_date)ASYearFROMorders
ORDERBY之後不可使用函數,例如:「SELECTorder_amountFROMordersORDERBYyear(order_date)」中year(order_date)是不合法的。修正:「SELECTorder_amount,year(order_date)ASyearFROMordersORDERBYyear」使用別名year!
9)
WHERE為記錄加設過濾條件在普通Foxpro語法中,FOR是為指令中顯示或處理的記錄加設條件。例如:REPLACEnameWITH'Ms.'+nameFORSEX='F'在SQL中,FOR的功能由WHERE代替了。a)單一條件selectcust_id,maxordamtfromcustomerwheremaxordamt>10000選取所有女性記錄進行取代工作
b)
複合條件
SQLnotes
第八頁
selectcust_id,maxordamtfromcustomerwheremaxordamt>10000andmaxordamt<20000
c)
IN直接設定記錄中字段須符合的內容。例如:SELECTcust_id,maxordamtFROMordersWHEREcust_idIN(3,7,9)直接指定cust_id必須是3、7或9。(上面的SQL語句可寫成:SELECTcust_id,maxordamtFROMordersWHEREcust_id=3orcust_id=7orcust_id=9)又例如:SELECTname,districtFROMstudent;WHEREdistrictIN('Mongkok','YauMaTei','Central')指定區域是旺角、油麻地或中環。
d)
BETWEEN..AND..在條件中指定字段所在的範圍。例如:SELECTcust_id,maxordamtFROMordersWHEREcust_idBETWEEN3AND8指定cust_id必須介乎3及8之間(包括3及8)。(上面的SQL語句可寫成:SELECTcust_id,maxordamtFROMordersWHEREcust_id>=3andcust_id<=8)又例如:SELECTname,districtFROMstudent;WHEREnameBETWEEN'Chau'AND'Ho'指定介乎姓'Chau'及'Ho'之間。
e)
SQLnotes
LIKE
第九頁
利用百搭(wildcards)符號_及%設定條件。_%是單一位百搭符號是任意位百搭符號
例如:
SELECTname,houseFROMstudentWHEREhouseLIKE'Choi_anHouse'中逢是'Choi?anHouse'都符合條件,好像'ChoiWanHouse'、'ChoiTanHouse'或'ChoiSanHouse'都是。
又例如:SELECTname,districtFROMstudentWHEREdistrictLIKE'Tai%'中逢是'Tai'字頭的都符合條件,好像'TaiPo'、'TaiO'或'TaiKokTsui'。
f)
複合LIKE/NOTLIKELIKE可配合and及or來增加條件的複雜性。例如:SELECTnameFROMstudent;WHERE(nameLIKE'Chan%'ornameLIKE'Yeung%')可選取姓陳或楊的學生。也可使用NOTLIKE來選取不符合條件的記錄。例如:SELECTnameFROMstudentWHEREnameNOTLIKE'Fai'可選取中沒有'Fai'字的學生。又例如:SELECTnameFROMstudent;WHERE(nameNOTLIKE'Chan%'ornameNOTLIKE'Yeung%')可選取不是姓陳及姓楊的學生。你知道下面的語句內條件是甚麼嗎?SELECTname,classno,districtFROMstudent;WHEREclassno>20ANDdistrict<>'Wanchai'AND;(nameLIKE'%Fung%'ORnameNOTLIKE'Chan%')
10)總計函數
SQLnotes第一○頁
在普通Foxpro指令中,下列是一些計算記錄的總和、平均值等函數:CALCULATECOUNT()數算記錄的數目
CALCULATESUM(field1)計算field1在記錄中的總和CALCULATEAVG(field1)計算field1在記錄中的平均值CALCULATEMAX(field1)計算field1在記錄中的最大值CALCULATEMIN(field1)計算field1在記錄中的最小值在SQL中,上列指令可融合在SQL語句中,並省略CALCULATE指令。例如:SELECTCOUNT(*)FROMstudentWHEREsex='M'就相等於SELECT*FROMstudentWHEREsex='M'結果就是數算有多少個男生。所產生的結果加上執行COUNT
又例如:SELECTCOUNT(DISTINCTtitle)FROMemployee就相等於SELECTDISTINCTtitleFROMemployee所產生的結果加上執行COUNT結果就是數算有多少個不同的title。
再例如:SELECTMAX(hire_date)AS最後日期FROMemployee顯示hire_date最大的值,並以最後日期為題。又例如:SELECTAVG(order_amt),MAX(order_amt),MIN(order_amt)FROMorders一次過顯示ord_amt的平均值、最大值及最小值。
SQLnotes
第一一頁在WHERE內是不可以用SUM,COUNT等總計函數的。例如:
11)GROUPBY...有著相同字段值的記錄在SQL中可利用GROUPBY組合起來。
只有10個不同的title。
SELECT*FROM
employeeGROUPBYtitle
留意:i.ii.每組只選取一個記錄顯示,所顯示的是在原表格中該組的最後一個記錄。結果表格中tile自動以升幕排序。
iii.上面的結果換轉是其他SQL系統而不是VisualFoxpro,可能有不同的結果。
SQLnotes
第一二頁
a)
GROUPBY與總計函數GROUPBY的威力要與總計函數配合時才顯現出來。例一:SELECTAVG(age)FROMstudentGROUPBYclass
得出的結果是列出每班學生的平均年齡,並依班別作升幕排序。
SQLnotes
第一三頁