字符串函數(shù)
合并字符串函數(shù)CONCAT()和CONCAT_WS
1. CONCAT()
函數(shù)定義為:CONCAT(S1,S2,...SN)
將傳入的參數(shù)連接起來返回所合并的字符串類型數(shù)據(jù)。如果其中一個參數(shù)為null冗酿,則返回值為null
SELECT CONCAT('my','null'); -- 返回結(jié)果為:mynull
SELECT CONCAT('my','s','ql',NULL); -- 返回結(jié)果為:NULL
除了可以傳入字符串,還可以傳入其他類型參數(shù)
SELECT CONCAT(CURDATE(),1); -- 返回結(jié)果為:當(dāng)前日期1(例:當(dāng)前日期為2019-08-01 則 返回結(jié)果為 2019-08-011)
-- 有表users孤钦,數(shù)據(jù)如下:
| id | name |
| 1? | haha |
| 2? | NULL |
SELECT CONCAT(u.`name`,'哈哈') FROM users u; -- 返回結(jié)果為:haha哈哈 | NULL
2. CONCAT_WS()
CONCAT_WS(SEP,S1,S2,...SN)
和CONCAT()比較:當(dāng)前函數(shù)多了一個表示分割符的SEP參數(shù)
SELECT CONCAT_WS(',',1,2); -- 返回結(jié)果:1,2
SELECT CONCAT_WS(NULL,1,2); -- 返回結(jié)果:NULL
SELECT CONCAT_WS('-',1,NULL,2); -- 返回結(jié)果:1-2
注:1. 分隔符為null時嗅钻,返回結(jié)果為null
? ? 2. 非分隔符的參數(shù)為null時,返回結(jié)果會忽略null奕污,返回其他參數(shù)且以分隔符進(jìn)行分隔
使用場景:如果有需要合并字段且需要使用符號來分隔每個字段值時姓蜂,可以使用CONCAT_WS()函數(shù)
3. GROUP_CONCAT()函數(shù)
語法:group_concat( [distinct] 要連接的字段 [order by 排序字段 asc/desc ?] [separator '分隔符'] )
將group by產(chǎn)生的同一個分組中的值連接起來按厘,返回一個字符串結(jié)果。
說明:通過使用distinct可以排除重復(fù)值钱慢;如果希望對結(jié)果中的值進(jìn)行排序逮京,可以使用order by子句;separator是一個字符串值束莫,缺省為一個逗號懒棉。
SELECT GROUP_CONCAT(DISTINCT(t2.`id`)),t2.`t2_name`
FROM tableA? t1
LEFT JOIN tableB t2 ON t1.`t1_id` = t2.`id`
WHERE t1.`t1_id` IN (0,8) GROUP BY t2.`t2_name`;
-- 返回t1_id為0和8 且 按t2_name字段值分組的
-- 所有不重復(fù)的tableB的id
-- 如果左后查詢出來的數(shù)據(jù)很大時,則需要使用下面的語句览绿,對查詢出來的數(shù)據(jù)加長度
SET group_concat_max_len = 1000;
參考文章:https://baijiahao.baidu.com/s?id=1595349117525189591&wfr=spider&for=pc
比較字符串大小函數(shù)
1. STRCMP()
STRCMP(str1,str2)
比較兩個字符串的大小策严,如果參數(shù)str1大于str2,則返回結(jié)果1饿敲;如果str1小于str2妻导,則返回-1;如果str1等于str2诀蓉,則返回0
SELECT STRCMP('a','a'); -- 返回結(jié)果:0
SELECT STRCMP('abc','abd'); -- 返回結(jié)果:-1
SELECT STRCMP('ac','abc'); -- 返回結(jié)果:1
問題:SELECT STRCMP('A','a');? -- 返回結(jié)果:0? 可能是因為mysql設(shè)置了不區(qū)分大小寫的原因?qū)е翧 和 a相等
注:strcmp()函數(shù)是根據(jù)ACSII碼的值來比較兩個字符串的栗竖;strcmp()函數(shù)首先將s1字符串的第一個字符值減去s2第一個字符,若差值為零則繼續(xù)比較下去渠啤;若差值不為零狐肢,則返回差值。
獲取字符串長度
1. LENGTH()
LENGTH(str) 獲取傳入的參數(shù)str的長度
SELECT LENGTH('apple'); -- 返回結(jié)果:5
SELECT LENGTH('蘋果'); -- 返回結(jié)果:6? 當(dāng)前使用utf8編碼
注:1. utf8字符集編碼下沥曹,一個漢字是算三個字符份名,一個數(shù)字或字母算一個字符。
? ? 2. 其他編碼下妓美,一個漢字算兩個字符僵腺,一個數(shù)字或字母算一個字符。
2. CHAR_LENGTH()
CHAR_LENGTH(str) 獲取傳入的參數(shù)str的字符數(shù)
SELECT CHAR_LENGTH('apple'); -- 返回結(jié)果:5
SELECT CHAR_LENGTH('蘋果'); -- 返回結(jié)果:2
注:1. 返回值為字符串string或者對應(yīng)字段長度壶栋,長度的單位為字符辰如,一個多字節(jié)字符(例如:漢字)算作一個單字符;
? ? 2. 不管漢字還是數(shù)字或者是字母都算是一個字符贵试;
? ? 3. 任何編碼下琉兜,多字節(jié)字符都算是一個字符;
實現(xiàn)字母大小寫的轉(zhuǎn)換函數(shù)
1. UPPER()
UPPER(s)? 將傳入的字符串對象s中所有字母全部轉(zhuǎn)換為大寫字母
當(dāng)然除了可以使用UPPER()毙玻,還可以用UCASE()函數(shù)來轉(zhuǎn)換
SELECT UPPER('hahei'); -- 返回結(jié)果:HAHEI
SELECT UCASE('xixi'); -- 返回結(jié)果:XIXI
2. LOWER()
LOWER(s)? 將傳入的字符串對象s中所有字母全部轉(zhuǎn)換為小寫字母
哈嘿豌蟋,當(dāng)然還可以使用LCASE()函數(shù)來轉(zhuǎn)換
SELECT LOWER('Hh'); -- 返回結(jié)果:hh
SELECT LCASE('A'); -- 返回結(jié)果:a
注:UPPER()和UCASE(),LOWER()和LCASE()沒啥區(qū)別
查找字符串
1. 返回字符串位置的FIND_IN_SET()函數(shù)
FIND_IN_SET(str1,str2) 返回在字符串str2中與str1相匹配的字符串的位置桑滩,參數(shù)str2中將包含若干個用逗號隔開的字符串
SELECT FIND_IN_SET('hh','hh ,haha,h h,hh,kk,hh');
-- 返回結(jié)果:4
2. 返回指定字符串位置的FIELD()函數(shù)
FIELD(str,str1,str2....) 返回第一個與字符串str匹配的字符串的位置
SELECT FIELD('hh','hh ','haha','h h','hh','kk','hh');
-- 返回結(jié)果:1
3. 返回子字符串相匹配的開始位置
LOCATE(str1,str)? 返回參數(shù)str中字符串str1的開始位置
POSITION(str1 IN str)
INSTR(str,str1)
SELECT LOCATE('h','12h3'); -- 返回結(jié)果:3
SELECT POSITION('k' IN 'klk'); -- 返回結(jié)果:1
SELECT INSTR('asdsd','ds'); -- 返回結(jié)果:3
4. 返回指定位置的字符串的ELT()函數(shù)
ELT(n,str1,str2...) 返回第n個字符串
SELECT ELT(2,'hh','kk','ll'); -- 返回結(jié)果:kk
從現(xiàn)有字符串中截取子字符串
1. 從左邊或右邊截取子字符串
LEFT(str,num) 返回字符串str中的包含前num個字母(從左邊數(shù))的字符串
RIGHT(str,num) 返回字符串str中的包含前num個字母(從右邊數(shù))的字符串
SELECT LEFT('hahei',2); -- 返回結(jié)果:ha
SELECT RIGHT('abc',2); -- 返回結(jié)果:bc
2. 截取指定位置和長度子字符串
SUBSTRING(str,num,len)? 返回字符串str中的第num個位置開始長度為len的子字符串
SELECT SUBSTRING('substring',4,3); -- 返回結(jié)果:str
去除字符串的首尾空格
1. 去除字符串開始處空格
LTRIM(str)? 返回去掉開始處左邊空格的字符串
SELECT LTRIM(' h h '); -- 返回結(jié)果:[h h ]? 這里使用中括號括起來梧疲,使最后一個空格看的比較清楚
2. 去掉結(jié)尾處空格
RTRIM(str)? 返回去掉開始處右邊空格的字符串
SELECT RTRIM(' h h '); -- 返回結(jié)果:[ h h]? 這里使用中括號括起來,使第一個空格看的比較清楚
3. 去掉字符串首尾空格
TRIM(str)? 返回去掉首尾空格的字符串str
SELECT TRIM(' h h '); -- 返回結(jié)構(gòu):[h h]? 這里使用中括號括起來,使結(jié)果看的更清楚
替換字符串
1. INSERT()函數(shù)
INSERT(str,pos,len,newstr)? 將字符串str中的pos位置開始長度為len的字符串用字符串newstr來替換
SELECT INSERT('abc',2,3,'def'); -- 返回結(jié)果:adef
SELECT INSERT('abc',2,1,'def'); -- 返回結(jié)果:adefc
SELECT INSERT('abc',4,1,'def'); -- 返回結(jié)果:abc
SELECT INSERT('abc',4,1,NULL); -- 返回結(jié)果:NULL(不管哪個參數(shù)為null幌氮,結(jié)果都是null)
注:1. 如果參數(shù)pos的值超過字符串長度缭受,則返回值為原始字符串str
2. 如果len的長度大于原來字符串(str)中所剩字符串的長度,則從位置pos開始進(jìn)行全部替換
3. 如果任何一個參數(shù)為NULL浩销,則返回值為NULL
2. REPLACE()函數(shù)
REPLACE(str,substr,newstr)? 將字符串str中的子字符串substr用字符串newstr來替換
SELECT REPLACE('abc','b','ef'); -- 返回結(jié)果:aefc
SELECT REPLACE('abc','d','ef'); -- 返回結(jié)果:abc
使用日期和時間函數(shù)
1. 獲取當(dāng)前日期和時間
NOW()贯涎,CURRENT_TIMESTAMP(),LOCALTIME()慢洋,SYSDATE()
SELECT NOW(),CURRENT_TIMESTAMP(),LOCALTIME(),SYSDATE(),
SLEEP(2),
NOW(),CURRENT_TIMESTAMP(),LOCALTIME(),SYSDATE();
-- 返回結(jié)果(當(dāng)前時間為2019-09-09 21:25:09):
? ? -- 第一行結(jié)果都是 2019-09-09 21:25:09
? ? -- sleep(2) 意為等待2秒
? ? -- 第三行:前三個函數(shù)值為2019-09-09 21:25:09? 最后一個為2019-09-09 21:25:11
注:CURRENT_TIMESTAMP是NOW的同義詞塘雳,也就是說兩者是相同的
? ? ? SYSDATE函數(shù)返回的是執(zhí)行到當(dāng)前函數(shù)時的時間,而NOW返回的是執(zhí)行SQL語句時的時間
2. 獲取當(dāng)前日期
CURRENT_DATE()普筹,CURDATE()
SELECT CURRENT_DATE(),CURDATE();
-- 當(dāng)前日期2019-09-09败明,返回結(jié)果為:2019-09-09
SELECT CURDATE()+0;
-- 當(dāng)前日期2019-09-09,返回結(jié)果:20190909
3. 通過各種方式顯示日期和時間
3.1 通過UNIX方式顯示日期和時間
所謂UNIX太防,是Unix epoch妻顶、Unix time,POSIX time或Unix timestamp的縮寫蜒车,中文為時間戳讳嘱。根據(jù)ISO-8601規(guī)范,該方式將顯示從1970年1月1日開始所經(jīng)過的秒數(shù)酿愧。即一分鐘使用UNIX時間戳表示為:60秒沥潭,一小時表示為3600秒,一天24小時則為86400秒嬉挡。
UNIX_TIMESTAMP()? 函數(shù)返回時間戳格式的時間
FROM_UNIXTIME()? 函數(shù)將時間戳格式時間轉(zhuǎn)換成普通格式的時間
-- 函數(shù)返回時間戳格式的時間
SELECT UNIX_TIMESTAMP('2019-09-09 22:09:00');? -- 返回結(jié)果:1568038140
-- 函數(shù)將時間戳格式時間轉(zhuǎn)換成普通格式的時間
SELECT FROM_UNIXTIME(1568038140);? -- 返回結(jié)果:2019-09-09 22:09:00
3.2 通過UTC方式顯示日期和時間
UTC是Universal Coordinated Time的縮寫钝鸽,中文為國際協(xié)調(diào)時間。Mysql提供了兩個函數(shù)UTC_DATE()和UTC_TIME()來實現(xiàn)日期和時間的UTC格式顯示
SELECT UTC_DATE(); -- 返回結(jié)果(返回當(dāng)前日期):2019-09-09
SELECT UTC_TIME(); -- 返回結(jié)果:13:15:25? 與當(dāng)前時間相差8小時
注:UTC_TIME()函數(shù)返回的時間與當(dāng)前時間有時區(qū)相差
3.3 獲取日期和時間各部分值
YEAR()? 返回日期中的年份
QUARTER()? 返回日期屬于第幾個季度
MONTH()? 返回日期屬于第幾個月
WEEK()? 返回日期屬于第幾個星期
DAYOFMONTH()? 返回日期屬于當(dāng)前月的第幾天
HOUR()? 返回時間的小時
MINUTE()? 返回時間的分鐘
SECOND()? 返回時間的秒
SELECT YEAR('2019-09-09 21:29:18'),? -- 返回結(jié)果:2019
QUARTER('2019-09-09 21:29:18'),? -- 返回結(jié)果:3
MONTH('2019-09-09 21:29:18'), -- 返回結(jié)果:9
WEEK('2019-09-09 21:29:18'), -- 返回結(jié)果:36
DAYOFMONTH('2019-09-09 21:29:18'), -- 返回結(jié)果:9
HOUR('2019-09-09 21:29:18'),? -- 返回結(jié)果:21
MINUTE('2019-09-09 21:29:18'),? -- 返回結(jié)果:29
SECOND('2019-09-09 21:29:18');? -- 返回結(jié)果:18
4. 計算日期和時間的函數(shù)
4.1 DATEDIFF(date1,date2)? 返回日期參數(shù)date1和date2之間相隔天數(shù)
SELECT DATEDIFF('2019-08-05','2019-08-03');? -- 返回結(jié)果:2
4.2 與指定日期和時間操作
ADDDATE(date,n)? 計算日期參數(shù)date加上n天后的日期
SUBDATE(date,n)? 計算日期參數(shù)date減去n天后的日期
SELECT ADDDATE('2019-09-01',2); -- 返回結(jié)果:2019-09-03
SELECT SUBDATE('2019-09-01',2); -- 返回結(jié)果:2019-08-30
SELECT ADDDATE('2019-09-01',INTERVAL 2 DAY);? -- 返回結(jié)果:2019-09-03
SELECT SUBDATE('2019-09-01',INTERVAL 2 DAY);? -- 返回結(jié)果:2019-08-30
ADDDATE(d,INTERVAL,expr type)? 返回日期參數(shù)d加上一段時間后的日期庞钢,表達(dá)式參數(shù)expr決定了時間的長度拔恰,參數(shù)type決定了所操作的對象
SUBDATE(d,INTERVAL,expr type)? 返回日期參數(shù)d減去一段時間后的日期,表達(dá)式參數(shù)expr決定了時間的長度基括,參數(shù)type決定了所操作的對象
這里type的取值:
type? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 含義? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? expr表達(dá)式
YEAR? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 年? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? YY
MONTH? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 月? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? MM
DAY? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 日? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? DD
HOUR? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 小時? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? hh
MINUTE? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 分鐘? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? mm
SECOND? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 秒? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ss
YEAR_MONTH? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 年和月? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? YY與MM之間用任意符號隔開
DAY_HOUR? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 日和小時? ? ? ? ? ? ? ? ? ? ? ? ? ? ? DD與hh之間用任意符號隔開
DAY_MINUTE? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 日和分鐘? ? ? ? ? ? ? ? ? ? ? ? ? ? DD與mm之間用任意符號隔開
DAY_SECOND? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 日和秒? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? DD與ss之間用任意符號隔開
HOUR_MINUTE? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 小時和分鐘? ? ? ? ? ? ? ? ? ? ? ? ? hh與mm之間用任意符號隔開
HOUR_SECOND? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 小時和秒? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? hh與ss之間用任意符號隔開
MINUTE_SECOND? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 分鐘和秒? ? ? ? ? ? ? ? ? ? ? ? ? ? ? mm與ss之間用任意符號隔開
DATE_FORMAT(date颜懊,format)? 根據(jù)參數(shù)對date進(jìn)行格式化
SELECT DATE_FORMAT('2019-09-01 22:23:00','%Y-%m-%d'); -- 返回結(jié)果:2019-09-01
SELECT DATE_FORMAT('2019-09-01 22:23:00','%H:%i:%s'); -- 返回結(jié)果:22:23:00
SEC_TO_TIME(seconds) 把秒數(shù)轉(zhuǎn)化為時間
TIME_TO_SEC(time)? 把時間轉(zhuǎn)化為秒數(shù)
SELECT SEC_TO_TIME(32400);? -- 返回結(jié)果:09:00:00
SELECT TIME_TO_SEC('09:00:00');? -- 返回結(jié)果:32400
MAKEDATE(year,dayofyear)? 根據(jù)參數(shù)(年份,第多少天)獲取日期
SELECT MAKEDATE(2019,2); -- 返回結(jié)果:2019年的第二天 2019-01-02
其他函數(shù)
SELECT IF(NAME = 'A1',1,0) FROM students;?
-- 返回結(jié)果:如果name的值為A1风皿,則返回1饭冬,否則返回0
SELECT IFNULL(name1,0) FROM students;
-- 返回結(jié)果:如果name1的值為null,則返回0揪阶,否則返回name1的值
比如有配置項影響了統(tǒng)計結(jié)果的時候,可以使用if函數(shù)患朱,就不用再去寫兩個sql了
HEX()函數(shù):返回十六進(jìn)制值的字符串表示形式鲁僚。注意:并不是十進(jìn)制轉(zhuǎn)化為十六進(jìn)制數(shù),而是轉(zhuǎn)化為字符串
UNHEX() 函數(shù):每對十六進(jìn)制數(shù)字轉(zhuǎn)化為一個字符