四、SQL函数②(字符串函数)

字符串函数:用户的密码、电子邮箱地址、证件号码等都是以字符串类型保存在数据库中的。

计算字符串长度

LENGTH()函数用来计算一个字符串的长度。该函数接受一个参数,此参数为待计算的字符串表达式,在MYSQLServer 中这个函数名称为LEN()。
如:

MYSQL,Oracle,DB2:
SELECT FName, LENGTH(FName) FROM T_Person

MSSQLServer:
SELECT FName, LEN(FName) FROM T_Person

字符串转换为小写

LOWER()函数用来将一个字符串转换为小写。该函数接受一个参数,此参数为待转换的字符串表达式,在DB2 中这个函数名称为LCASE()。如下SQL语句:

MYSQL,MSSQLServer,Oracle:
SELECT FName, LOWER(FName) FROM T_Person

DB2:
SELECT FName, LCASE(FName) FROM T_Person

字符串转换为大写

UPPER()函数用来将一个字符串转换为大写。该函数接受一个参数,此参数为待转换的字符串表达式,在DB2中这个函数名称为UCASE ()。如下面SQL语句:

MYSQL,MSSQLServer,Oracle:
SELECT FName, UPPER(FName) FROM T_Person

DB2:
SELECT FName, UCASE(FName) FROM T_Person

截去字符串左侧空格

LTRIM()函数用来将一个字符串左侧的空格去掉。该函数接受一个参数,此参数为待处理的字符串表达式。如下的SQL语句:

SELECT FName,LTRIM(FName),LTRIM("abc") FROM T_Person

截去字符串右侧空格

RTRIM ()函数用来将一个字符串左侧的空格去掉。该函数接受一个参数,此参数为待处理的字符串表达式。如下的SQL语句:

SELECT FName,RTRIM(FName),RTRIM("abc") FROM T_Person

截去字符串两侧的空格

TRIM ()函数用来将一个字符串两侧的空格去掉。该函数接受一个参数,此参数为待处理的字符串表达式。此函数只在MYSQL 和Oracle 中提供支持,在MSSQLServer和DB2中可以使用LTRIM()函数和RTRIM()函数复合来进行变通实现,也就是用LTRIM(RTRIM(string))来模拟实现TRIM (string)。
如:

MYSQL,Oracle:
SELECT FName,TRIM(FName),TRIM(" abc ") FROM T_Person

MSSQLServer,DB2:
SELECT FName,LTRIM(RTRIM(FName)),LTRIM(RTRIM(" abc ")) FROM T_Person

取子字符串

字符串是由多个字符组成的串,比如“HelloWorld”在内存是如下存储的:

1 2 3 4 5 6 7 8 9 10
H e l l o W o r l d

表格第一行的数字表示组成字符串的每个字符的位置,第二行则为各个位置上的字符。由这些字符中连续的多个字符还可以组成新的字符串,新的字符串则被称为“子字符串”。
如:从第3 个字符到第5 个字符组成的“llo”就是一个子字符串,我们也可以称“llo”为从第3 个字符开始长度为3 的子字符串。

计算子字符串的函数SUBSTRING(),其参数格式如下:

SUBSTRING(string,start_position,length)

其中参数string为主字符串,start_position为子字符串在主字符串中的起始位置,length为子字符串的最大长度。
在MYSQL和MSSQLServer 中支持这个函数,在Oracle和DB2中这个函数的名称为SUBSTR()
如下的SQL语句:

MYSQL、MSSQLServer:
SELECT SUBSTRING("abcdef111",2,3)

Oracle:
SELECT SUBSTR("abcdef111",2,3) FROM DUAL

DB2:
SELECT SUBSTR("abcdef111",2,3) FROM SYSIBM.SYSDUMMY1

执行结果:

SUBSTRING("abcdef111",2,3)
bcd

再如下的SQL语句:

MYSQL,MSSQLServer:
SELECT FName, SUBSTRING(FName,2,3) FROM T_Person

Oracle,DB2:
SELECT FName, SUBSTR(FName,2,3) FROM T_Person

执行结果:

FName SUBSTRING(FName,2,3)
Tom om
Jim im
Lily ily
Kelly ell
Sam am
Kerry err
Smith mit
BillGates ill

计算子字符串的位置

用于检测制定的子字符串是否存在于主字符串中,如果存在则还可以返回所在的位置。该函数在MYSQL 和Oracle中名称为INSTR,其参数格式如下:

INSTR(string,substring)

其中参数string为主字符串,参数substring为待查询的子字符串。如果string中存在substring子字符串,则返回子字符串第一个字符在主字符串中出现的位置;如果string中不存在substring子字符串,则返回0。

在MSSQLServer中这个函数名为CHARINDEX,其参数格式以及返回值规则与MYSQL以及Oracle一致。

在DB2中这个函数名为LOCATE,其返回值规则与前述几种数据库系统一致,不过参数格式与它们正好相反,其参数格式如下:

LOCATE(substring,string)

其中参数substring为待查询的子字符串,参数string为主字符串,也就是两个参数的位置是与其它集中数据库系统相反的。如下的SQL语句:

MYSQL,Oracle:
SELECT FName, INSTR(FName,"m") , INSTR(FName,"ly") FROM T_Person

MSSQLServer:
SELECT FName,CHARINDEX(FName,"m"), CHARINDEX(FName,"ly") FROM T_Person

DB2:
SELECT FName, LOCATE("m",FName) , LOCATE("ly",FName) FROT_Person

从左侧开始取子字符串

使用SUBSTRING()函数:从任意位置开始取任意长度的子字符串,不过有的时候我们只需要从左侧开始取子字符串,这样指定主字符串和要取的长度就可以了,不过如果使用SUBSTRING()函数的话仍然需要指定三个参数,其中第二个参数为常量1。MYSQL、MSSQLServer、DB2 中提供了LEFT()函数用于从左侧开始取任意长度的子字符串,其参数格式如下:

LEFT (string,length)

其中参数string为主字符串,length为子字符串的最大长度。

Oracle 不支持LEFT()函数,但能使用SUBSTR()函数进行变通实现,即:SUBSTR(string, 1, length)。

如下的SQL语句:

MYSQL,MSSQLServer,DB2:
SELECT FName, LEFT(FName,3) , LEFT(FName,2) FROM T_Person

Oracle:
SELECT FName,SUBSTR(FName, 1,3),SUBSTR(FName, 1,2) FROM T_Person

从右侧开始取子字符串

SUBSTRING()函数:从任意位置开始取任意长度的子字符串,不过有的时候我们只需要从右侧开始取子字符串,这样指定主字符串和要取的长度就可以了,不过如果使用SUBSTRING()函数的话仍然需要指定三个参数。
MYSQL、MSSQLServer、DB2 中提供了RIGHT ()函数:用于从左侧开始取任意长度的子字符串,其参数格式如下:

RIGHT (string,length)

其中参数string为主字符串,length为子字符串的最大长度。

Oracle中不支持RIGHT ()函数,只能使用SUBSTR()函数进行变通实现,其中起始位置用如下表达式计算出来:startposition= LENGTH(string)- length+1
注:SUBSTR(string, LENGTH(string)- length+1, length)等价于RIGHT (string,length)。

执行下面的SQL语句:

MYSQL,MSSQLServer,DB2:
SELECT FName, RIGHT(FName,3) , RIGHT(FName,2) FROM T_Person

Oracle:
SELECT FName,SUBSTR(FName, LENGTH(FName)-3 +1, 3),SUBSTR(FName, LENGTH(FName)-2 +1, 2) FROM T_Person

字符串替换

REPLACE()函数:用来将字符串的指定的子字符串替换为其它的字符串。
如:
将“Hello World”中的“rl”替换为“ok”后得到“Hello Wookd”
把“Just so so”中的“s”替换为“z”后得到“Juzt zo zo”

REPLACE()函数的参数格式如下:

REPLACE(string,string_tobe_replace,string_to_replace)

其中参数string为要进行替换操作的主字符串,参数string_tobe_replace为要被替换的字符串,而string_to_replace将替换string_tobe_replace中所有出现的地方。如下的SQL语句:

select FName,REPLACE(FName,"i","e"),
FIDNumber,REPLACE(FIDNumber,"2345","abcd") FROM T_Person

SQL中没提供删除字符串中匹配的子字符串的方法,但使用REPLACE()函数就可以达到删除子字符串的方法,即:将第三个参数设定为空字符串,用空字符串来替换匹配的子字符串,就能达到了删除指定子字符串的效果
如:将FName中的m以及FIDNumber 中的123 删除

SELECT FName, REPLACE(FName,"m","") ,FIDNumber,
REPLACE(FIDNumber,"123","") FROM T_Person

LTRIM()、RTRIM()和TRIM()都只能删除两侧的字符串,无法删除字符串中间的空格,而使用REPLACE()函数也可以完成这个功能,也就是用空字符串替换中所有的空格。执行下面的SQL语句:

MYSQL、MSSQLServer:
SELECT REPLACE(" abc 123 wpf"," ",""),REPLACE(" ccw enet wcf f"," ","")

Oracle:
SELECT REPLACE(" abc 123 wpf"," ",""),REPLACE(" ccw enet wcf f"," ","") FROM DUAL

DB2:
SELECT REPLACE(" abc 123 wpf"," ",""),REPLACE(" ccw enet wcf f"," ","") FROM SYSIBM.SYSDUMMY1

得到字符的ASCII码

ASCII()函数用来得到一个字符的ASCII码,它有且只有一个参数,该参数为待求ASCII码的字符,若参数为一个字符串则函数返回第一个字符的ASCII码,如:

MYSQL,MSSQLServer:
SELECT ASCII("a") , ASCII("abc")
Oracle:
SELECT ASCII("a") , ASCII("abc") FROM DUAL
DB2:
SELECT ASCII("a") , ASCII("abc") FROM SYSIBM.SYSDUMMY1

执行结果:

ASCII("a") ASCII("abc")
97 97

再如:计算每个员工姓名的第一个字符的ASCII码:

MYSQL,MSSQLServer,DB2:
SELECT FName, LEFT(FName,1),ASCII(LEFT(FName,1)),
ASCII(FName) FROM T_Person

Oracle:
SELECT FName,SUBSTR(FName,1,1),
ASCII(SUBSTR(FName, 1,1)),ASCII(FName) FROM T_Person

得到一个ASCII码数字对应的字符

与 ASCII()函数正好相反,该函数用来得到一个字符的ASCII 码的函数。
在MYSQL、MSSQLServer 和DB2 中该函数为:CHAR(),在Oracle中该函数的名字则为CHR()

执行下面的SQL语句:

MYSQL,MSSQLServer:
SELECT CHAR(56),CHAR(90),"a",CHAR(ASCII("a"))

Oracle:
SELECT CHR(56),CHR(90),"a",CHR(ASCII("a")) FROM DUAL

DB2:
SELECT CHR(56),CHR(90),"a",CHR( ASCII("a")) FROM SYSIBM.SYSDUMMY1

执行结果:

CHAR(56) CHAR(90) a CHAR( ASCII("a") )
8 Z a a

如:将FWeight转换为整数,得到它对应的字符:

MYSQL、MSSQLServer:
SELECT FWeight, CEILING(FWeight),CHAR( CEILING(FWeight) ) FROM T_Person

Oracle:
SELECT FWeight, CEIL(FWeight),CHAR( CEIL(FWeight) ) FROM T_Person

DB2:
SELECT FWeight, CEILING(FWeight),CHAR(int(CEILING(FWeight))) FROM T_Person

由于DB2 的类型检查机制非常严格,所以在DB2 中需要用int()函数将CEILING()函数的返回值显示的转换为整数类型。

发音匹配度

到目前为止所有关于字符串的匹配都是针对其拼写形式的。
如:检索年龄为“jack”的员工:

[code=java]

SELECT * from T_Person WHERE FName="jack"

[/code]

有时我们不知道一个人姓名的准确拼写,只知道它的发音,如“检索名字发音为和[jeck]类似的人员”,就要进行发音的匹配度测试

SOUNDEX()函数:用于计算一个字符串的发音特征值,这个特征值为一个四个字符的字符串,特征值的第一个字符总是初始字符串中的第一个字符,而其后则是一个三位数字的数值。
如:查询几个名字的发音特征值:

MYSQL,MSSQLServer:
SELECT SOUNDEX("jack"),SOUNDEX("jeck"),
SOUNDEX("joke"),SOUNDEX("juke"),
SOUNDEX("look"),SOUNDEX("jobe")

Oracle:
SELECT SOUNDEX("jack"),SOUNDEX("jeck"),
SOUNDEX("joke"),SOUNDEX("juke"),
SOUNDEX("look"),SOUNDEX("jobe") FROM DUAL

DB2:
SELECT SOUNDEX("jack"),SOUNDEX("jeck"),
SOUNDEX("joke"),SOUNDEX("juke"),
SOUNDEX("look"),SOUNDEX("jobe") FROM SYSIBM.SYSDUMMY1

执行结果:

SOUNDEX("jack")
SOUNDEX("jeck")
SOUNDEX("joke")
SOUNDEX("juke")
SOUNDEX("look")
SOUNDEX("jobe")
J000 J000 J000 J000 L200 J100

可以看到jack、jeck、joke、juke 几个字符串的发音非常相似,而look、jobe 的发音则和它们差距比较大。
再如:查询公司所有员工姓名的发音特征值:

SELECT FName, SOUNDEX(FName) FROM T_Person

执行结果:

FName SOUNDEX(FName)
Tom T500
Jim J500
Lily L000
Kelly K400
Sam S500
Kerry K600
Smith S530
BillGates B4232

在MSSQLServer和DB2中提供了DIFFERENCE()用来简化两个字符串的发音相似度比较,它可以计算两个字符串的发音特征值,并且比较它们,然后返回一个0至4之间的一个值来反映两个字符串的发音相似度,这个值越大则表示两个字符串发音思想度越大。

如:计算每个人的姓名发音与“Merry”的相似度:

SELECT DIFFERENCE(FName,"Merry") FROM T_Person

执行结果:

FName
Tom Merry 2
Jim Merry 1
Lily Merry 2
Kelly Merry 3
Sam Merry 2
Kerry Merry 3
Smith Merry 0
BillGates Merry 1

可以看到Kerry、Kelly与Merry的发音相似度非常高。

在WHERE语句中使用DIFFERENCE()更有意义
如:查询和“Tim”发音相似度大于3 的员工:

SELECT * FROM T_Person WHERE DIFFERENCE(FName,"Tim")>=3
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 199,636评论 5 468
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 83,890评论 2 376
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 146,680评论 0 330
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 53,766评论 1 271
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 62,665评论 5 359
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,045评论 1 276
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,515评论 3 390
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,182评论 0 254
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,334评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,274评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,319评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,002评论 3 315
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,599评论 3 303
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,675评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,917评论 1 255
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,309评论 2 345
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 41,885评论 2 341

推荐阅读更多精彩内容

  • 字符串函数 在开发T-SQL时,经常会需要对字符串进行各种各样的操作,下面介绍常用的字符串函数。 1、获取字符的A...
    道素阅读 1,197评论 0 2
  • pyspark.sql模块 模块上下文 Spark SQL和DataFrames的重要类: pyspark.sql...
    mpro阅读 9,438评论 0 13
  • 语 句 功 能 数据操作 SELECT——从数据库表中检索数据行和列INSERT——向数据库表添加新数据行DELE...
    戰敭阅读 5,056评论 0 53
  • Author:杜七 Date:2017.03.15 字符串截取 MySQL 字符串截取函数:left(), rig...
    杜七阅读 613评论 0 2
  • MSSQL 跨库查询(臭要饭的!黑夜) 榨干MS SQL最后一滴血 SQL语句参考及记录集对象详解 关于SQL S...
    碧海生曲阅读 5,526评论 0 1