存儲在表中的數據通常不是應用程序所須要的格式。咱們須要直接從數據庫中檢索出轉換、計算或格式化的數據。而不僅是檢索出數據,而後再到應用程序或報告程序中區格式化。 mysql
這就發揮了計算字段的做用了。與前面的字段不一樣,計算字段並不實際存在於數據庫中。計算字段是運行時在SELECT 語句中建立的。 算法
須要注意的是,只有SELECT語句知道那些列是實際列,哪些列不是,客戶機的角度來看,計算字段和其餘字段是同樣的。 sql
拼接字段 數據庫
拼接:將值聯結到一塊兒構成單個值。 函數
生成供應商 columnOne(columnTwo) 的格式 測試
SELECT Concat(columnOne, '(' , columnTwo, ')') FROM table ORDER BY columnOne; spa
使用別名 orm
別名使用AS關鍵字賦予 排序
執行算術運算 產品
另外一常見的用途就是對檢索出來的數據進行算術運算。
例如:檢索出column_id 爲2005的columnOne乘以columnTwo的值
SELECT column_id, columnOne, columnTwo, columnOne*columnTwo AS column_price FROM table WHERE column_id = 2005
操做符 + - * /
SELECT 3*2;將返回6
SELECT Now(); 返回當前的日期和時間
第十一章 使用數據處理函數
SQL實現了一下類型的函數
1 用於處理文本串,如刪除、填充、裝換大小寫
2 用於數據上進行的算術操做,如返回絕對值,進行代數運算
3用於處理日期和時間值並從這些值中提取特定的成分,如返回兩個日期差,檢查日期有效性
4 返回DBMS正使用的特殊信息 ,如用戶登陸信息,檢查版本細節信息
文本處理函數
Upper() 將文本轉換爲大寫
SELECT vend_name, Upper(vend_name) AS vend_name_upcase FROM vendors ORDER BY vend_name;
經常使用的文本處理函數
Left() 返回串左邊的字符
Length() 返回串的長度
Locate() 找出串的一個子串
Lower() 將串轉換爲小寫
Right() 返回右邊的字符
Soundex() 返回串的SOUNDEX值
SubString() 返回串的字符
Upper() 將串轉換ewing大寫
Soundex()是一個將任何文字串轉換爲描述語音表示的字母數字模式的算法。他考慮了相似發信字符和音節,使得能對串進行發音的比較而不是字母比較,如:Y.lee搜索能夠匹配Y.lie
SELECT cust_name , cust_contact FROM customers WHERE Soundex(cust_contact) = Soundex('Y Lie')
刪除多餘空格的函數
RTrim() LTrim() Trim() 依次是刪除 右邊 左邊 兩邊的空格
SELECT Concat(RTrim(vend_name), '( ' ,RTrim(vend_country), ') FROM vendors ORDER BY vend_name;
日期和時間處理函數
日期和時間經常使用相應的數據類型和特點的格式存儲,以便能快速和有效的排序或過濾,並節省物理存儲空間。
AddDate() 增長一個日期 天、周等
AddTime() 增長一個時間 時、分等
CurDate() 返回當前日期
CurTime() 返回當前時間
Date() 返回日期時間的日期部分
DateDiff() 計算兩個日期之差
Date_Add() 高度靈活的日期或時間串
Date_Format() 返回一個格式的日期或時間串
Day() 返回一個日期的天數部分
DayOfWeek() 對於一個日期,返回對於星期幾
Hour() 返回一個時間的小時部分
Minute() 返回一個時間的分鐘部分
Moth() 返回一個日期的月份部分
Now() 返回當前的日期和時間
Second() 返回一個時間的秒部分
Time() 返回一個日期時間的時間部分
Year() 返回一個日期的年份部分
MySQl日期格式必須爲yyyy-mm-dd,如2010-05-03。雖然其餘日期格式也行,但這是首選格式,由於他排除了多義性。
例如,存儲的日期列中的日期是2010-11-05 15:23:05 若是想找出2010-11-05這天的數據,使用前面的語句就不行了。這是要使用Date()函數指示mysql提取列的日期的部分
SELECT cust_id, order_num FROM orders WHERE Date(order_date) = '2010-11-05';
檢索出2005-5月份的訂單怎麼辦呢?可使用BETWEEN
SELECT cust_id,order_num FROM orders WHERE Date(order_date) BETWEEN '2005-05-01' AND '2005-05-30';
還有一種不須要記住天數的函數Month(),使年份相等,再讓月份相等就好了
SELECT cust_id,order_num FROM orders WHERE Year(order_date) = 2005 AND Month(order_date) = 5;
數值處理函數
Abs() 返回一個數的絕對值
Cos() 返回一個角度的餘弦
Exp() 返回一個數的指數值
Mod() 返回除操做的餘數
Pi() 返回圓周率
Rand() 返回一個隨機數
Sin() 返回一個角度的正弦值
Sqrt() 返回一個數的平方根
Tan() 返回一角度的正切
第十二章 彙總函數
Msyql提供這些函數以便分析和報表生成,這種類型的檢索例子有如下幾種:
匯聚函數 :運行在行組上,計算和返回單個值的函數
1 肯定表中的行數(或者知足某個條件或包括某個特定的值的行數)
2 得到表中行組的和
3 找出表列(或全部行或某特定行的)最大值、最小值和平均值
AVG() 返回某列的平均值
COUNT() 返回某列的行數
MAX() 返回某列的最大值
MIN() 返回某列的最小值
SUM() 返回某列值之和
求products表中產品的平均價格
SELECT AVG(prod_price) AS avg_price FROM products;
求products表中編號爲1003產品的平均價格
SELECT AVG(prod_price) AS avg_price FROM products WHERE vend_id = 1003;
AVG()函數只能用來肯定特定數值列的平均值,並且名必須做爲函數參數給出。爲了得到多個平均值,必須使用多個AVG()函數,AVG()函數忽略列值爲NULL的行
COUNT()函數的兩種使用方式:
1 COUNT(*) 對錶中的數目進行計數,無論表列中包含的是NULL值仍是非空值
2 COUNT(column) 對特定的列中具備值的進行計數,忽略NULL值
SELECT COUNT(*) AS num_cust FROM customers;
SELECT COUNT(cust_email) AS num_cust FROM customers;
MAX()函數 ,忽略列值爲NULL的行
SELECT MAX() AS max_price FROM products;
MIN() 與MAX()函數同樣
SUM() 函數
SELECT SUM(quantity) AS items_ordered FROM orderitems WHERE order_num = 2005
下面是mysql5之後的函數 在mysql4中不能正常運行
DISTINCT 參數,做用是返回不相同的值
下面是返回供應商提供的產品的平均值,它與上面的SELECT 語句相同,但使用了DISTICT參數,所以平均值只考慮各個不一樣價格合起來的平均值
SELECT AVG(DISTINCT prod_price) AS avg_price FROM products WHERE vend_id=10003;
若是指定了列名,DISTINCT參數只能用於COUNT(),DISTINCT參數不能用於COUNT(*)應爲DISTINCT必須使用列名。
第十三章 分組數據
分組容許把數據分紅多個邏輯組,比便能對每一個組進行彙集計算。
分組是在SELECT 語句的 GROUP BY 子句中創建的。
返回每一個廠商提供了幾個產品
SELECT vend_id, COUNT(*) AS num_prods FROM products GROUP BY vend_id;
GROUP BY 一些重要規定
1 GROUP BY 子句能夠包含任意數目的列。這使得能對分組進行嵌套,爲數據分組提供了更細緻的控制
2 若是在GROUP BY 子句中嵌套了分組,數據將在最後規定的分組上進行彙總,換句話說,在創建分組時,指定的全部列都一塊兒計算(因此不能從個別列取回數據)
3 GROUP BY 子句列出的每一個列都必須是檢索列或有效的表達式,(但不能是彙集函數)若是。在SELECT 中使用了表達式,則必須在GROUP BY 子句中指定相同的表達式,不能使用別名。
4 除彙集計算語句外,SELECT 語句中的每一個列都必須在GROUP BY 子句中給出
5 若是分組列中具備NULL值,無論一個或多個都將做爲一個分組返回
6 GROUP BY 子句必須出如今WHERE 子句以後,GROUP BY 子句以前
過濾分組
如想要獲得大於3的不一樣產品訂單
WHERE 是過濾指定的行而不是列。 HAVING 支持全部 WHERE 操做符。
SELECT cust_id, COUNT(*) AS orders FROM orders GROUP BY cust_id HAVING COUNT(*) >3;
WHERE 是在分組前進行過濾, HAVING 是在分組後進行過濾
分組和排序區別
ORDER BY GROUP BY
排序產生的輸出 分組行,單輸出可能不是分組的順序
任意列均可以使用(甚至 只可能使用選擇列或表達式,並且必須使用每一個選擇列表達式
是分選擇列也可使用) 若是與彙集哈思楠一塊兒使用列(或表達式)則必須使用
不必定須要
例子:檢索總計訂單價格大於50的訂單號和總計訂單
SELECT order_num , SUM(quantity* item_price) AS ordertotal FROM orderitems GROUP BY order_num HAVING SUM(quantity*item_price) >= 50;
按訂單價格進行排序 ,後面加 ORDER BY ordertotal;
SELECT 子句順序
SELECT 要返回的列或表達式
FROM 從中檢索數據的表
WHERE 行級過濾
GROUNP BY 分組說明
HAVING 組級過濾
ORDER BY 輸出排序順序
LIMIT 要檢索的行數
第十三章 使用子查詢
Sql還容許使用子查詢,即嵌套在其餘查詢中的查詢。
利用子查詢進行過濾
SELECT cust_id FROM orders WHERE order_num IN(
SELECT order_num FROM orderitems WHERE prod_id = 'TNT2'
)
能夠把一條SELECT語句返回的結果用於另外一條SELECT語句的WHERE 子句
格式化sql 包含子查詢的sql語句難以閱讀,可使用適當的縮進。
獲得了訂購物品TNT2的全部客戶ID,下一步是檢索這些客戶的信息,總語句是
SELECT cust_name , cust_contact FROM customers WHERE cust_id IN(
SELECT cust_id FROM orders WHERE order_num IN (
SELECT order_num FROM orderitems WHERE prod_id = 'TNT2'
)
)
列必須匹配 在WHERE子句中使用子查詢,應該保證SELECT語句具備WHERE 子句中相同數目的列。一般子查詢將返回的單個列於單個列匹配,但若是須要也能夠多個列。
雖然子查詢通常與IN操做符結婚使用,但也能夠用於測試等於、不等於等符號
做爲計算字段使用子查詢
使用子查詢的另外一個方法是建立計算字段。
假設須要顯示sustomers表中每一個客戶的訂單總數。
SELECT cust_name ,cust_state,(
SELECT COUNT(*) FROM orders WHERE orders,coust_id = customers . Cust_id
) AS orders FROM customers ORDER BY cust_name;