一、简单查询 ZlP+t>
-tfUkGdx;l
简单的Transact-SQL查询只包括选择列表、FROM子句和WHERE子句。它们分别说明所查询列、查询的 b_^y
Ke^W
?NR&3q
表或视图、以及搜索条件等。 $4q$!jB5
G`RQl@W>)(
例如,下面的语句查询testtable表中姓名为“张三”的nickname字段和email字段。 ; Vpp1mk|
"3/&<0k
SELECT nickname,email wKKQAM6P1
P1ak>T*#2
FROM testtable B>g(i=E
wSi$.C2
WHERE name='张三' y/+IPR
qP]1}-
(一)选择列表 FG^lh
\/ipYc
选择列表(select_list)指出所查询列,它可以是一组列名列表、星号、表达式、变量(包括局部变 /xj`'8
9}5o> iR
量和全局变量)等构成。 VS >xvF
et?FX K"y
1、选择所有列 wf`A&P5tF
.wB'"z8L
例如,下面语句显示testtable表中所有列的数据: gloJ;dEB
d/!\iLF
SELECT * i` Q&5KL
;8a9S0eS
FROM testtable ~LQzt@G4
+lxjuEiae
2、选择部分列并指定它们的显示次序 R3%%;` c=
*wx95?H0Z
查询结果集合中数据的排列顺序与选择列表中所指定的列名排列顺序相同。 ERia5HnoD,
AEkjy h\
例如: Da8
|eN}
cQ
|Q-S
SELECT nickname,email G.`},c;A-
b!bg sd
FROM testtable voQJ!h1
`aTw!QBfG
3、更改列标题 #nw+U+qL
h'?v(k!
在选择列表中,可重新指定列标题。定义格式为: e;g7Ek3n
@S:T8
*~}
列标题=列名 qw1W}+~g
#k?. dWZ!
列名 列标题 L9-Jwy2(>
p=odyf1hK
如果指定的列标题不是标准的标识符格式时,应使用引号定界符,例如,下列语句使用汉字显示列 7ug"SV6Hb
HLOrDlj7
标题: 3?&v:H
GUZ.Pw
SELECT 昵称=nickname,电子邮件=email I]hjv
YgdQC(ib
FROM testtable V0BT./ B\<
D|ra ;d
4、删除重复行 )K$YL='kX
;dPaWS1D
SELECT语句中使用ALL或DISTINCT选项来显示表中符合条件的所有行或删除其中重复的数据行,默认 U!NuiKaQ26
g9fYt&
为ALL。使用DISTINCT选项时,对于所有重复的数据行在SELECT返回的结果集合中只保留一行。 U8J9 #+:
lrj&60R`w
5、限制返回的行数 XRO(p`OE-
< Sgc6>)
使用TOP n [PERCENT]选项限制返回的数据行数,TOP n说明返回n行,而TOP n PERCENT时,说明n是 &>]U c%JK
m2"wMt"*V
表示一百分数,指定返回的行数等于总行数的百分之几。 *V7mM?
8&M<?oe
例如: ="v`W'Pd
eh>
|m>JY
SELECT TOP 2 * 0N~kq-6.\
?|98Y"w
FROM testtable (~o"*1fk>
+80bG(I_
SELECT TOP 20 PERCENT * P;o{t
,n[<[tkCR
FROM testtable *5.wwV
NyT%S?@y<
(二)FROM子句 @HPr;m!
OTE,OCB[
FROM子句指定SELECT语句查询及与查询相关的表或视图。在FROM子句中最多可指定256个表或视图, IT{c:jo1{`
PpKjjA<
它们之间用逗号分隔。 zyhM*eM.7
^b$_I31D
在FROM子句同时指定多个表或视图时,如果选择列表中存在同名列,这时应使用对象名限定这些列 (qvH=VTwP
Q4_r) &np
所属的表或视图。例如在usertable和citytable表中同时存在cityid列,在查询两个表中的cityid时应 o$eCd{HuX
;mT}Q;F#
使用下面语句格式加以限定: : NA(nA
3
3UaW+@
SELECT username,citytable.cityid ^ghYi|kQq
qxDMDMN
FROM usertable,citytable "T{WOGU+
Hy1$Kvub
WHERE usertable.cityid=citytable.cityid }Nd1'BVf
e4,SR(O>
在FROM子句中可用以下两种格式为表或视图指定别名: f;Oh"Yt
Zp^O1&\SK?
表名 as 别名 v/9DD% An
!Ve0 :$
表名 别名 w7.,ch
1Acs0`3
例如上面语句可用表的别名格式表示为: tsL
; wT_
l
_%<U
SELECT username,b.cityid ^8_yJ=~V
]XbMqHGS
FROM usertable a,citytable b i@.Tv.NZ
8toOdh
WHERE a.cityid=b.cityid sv?Fx;d
%~x?C4L8
SELECT不仅能从表或视图中检索数据,它还能够从其它查询语句所返回的结果集合中查询数据。 ah hl
LXh}U>a9
例如: icIn>i<m
Zp3-Yo w2
SELECT a.au_fname+a.au_lname >h)kbsSU0z
bXvO+I<
FROM authors a,titleauthor ta `-.2Z
0
@fYVlHT%E
(SELECT title_id,title r
dSL
8-NycG&)
FROM titles cz1 + XpU
X!K> .r_Dg
WHERE ytd_sales>10000 `(h^z>%
nAWb9Yk
) AS t n0T|U
S4`X^a}pY
WHERE a.au_id=ta.au_id @B(oq1i@
oe] *Q
AND ta.title_id=t.title_id :`zO%h
P%lD9<jED
此例中,将SELECT返回的结果集合给予一别名t,然后再从中检索数据。 s{R,- \_
vhbHt_!u&
(三)使用WHERE子句设置查询条件 ^;<d<V}*
QMz =e
WHERE子句设置查询条件,过滤掉不需要的数据行。例如下面语句查询年龄大于20的数据: c0'ryS_Z9
D<d,9 S,)
SELECT * 8 5X}CCQ
lUB?eQuN_
FROM usertable Jh 0Grq
" Q?~LB
WHERE age>20 wR@>U.XT@
:\P@c(c{^C
WHERE子句可包括各种条件运算符: ~Ym_ {
$uDgBZA\
比较运算符(大小比较):>、>=、=、<、<=、<>、!>、!< p$9Aadi]
/ Qd` ?
范围运算符(表达式值是否在指定的范围):BETWEEN…AND… U,#x\[3!Jt
;7qIm83
NOT BETWEEN…AND… ,\iHgsZ
G9^`cTvv'8
列表运算符(判断表达式是否为列表中的指定项):IN (项1,项2……) Z! O4hA4
M,_
$s,
NOT IN (项1,项2……) G|KA!q
!i~(h&z
模式匹配符(判断值是否与指定的字符通配格式相符):LIKE、NOT LIKE G|f9l?p
cVW7I
空值判断符(判断表达式是否为空):IS NULL、NOT IS NULL BYX c
'K
Zh;wQCDj
逻辑运算符(用于多条件的逻辑连接):NOT、AND、OR }W8A1-UF
W&Fm;m@M
1、范围运算符例:age BETWEEN 10 AND 30相当于age>=10 AND age<=30 9GH5
8#yu.\N.xt
2、列表运算符例:country IN ('Germany','China') &>,]YrU
d<7b<f"~
3、模式匹配符例:常用于模糊查找,它判断列值是否与指定的字符串格式相匹配。可用于char、 yy8-t2V
Kh\ 7%>K#
varchar、text、ntext、datetime和smalldatetime等类型查询。 jeWv~JA%L|
&|{1Ws
可使用以下通配字符: cl4z%qv*
ih".y3
百分号%:可匹配任意类型和长度的字符,如果是中文,请使用两个百分号即%%。 ^#<L!yo^
v#qd q!64
下划线_:匹配单个任意字符,它常用来限制表达式的字符长度。 7-K8u
]}!@'+=
方括号[]:指定一个字符、字符串或范围,要求所匹配对象为它们中的任一个。 iVn4eLK^v
JkJ
@bh
Eu
[^]:其取值也[] 相同,但它要求所匹配对象为指定字符以外的任一个字符。 ")Not$8
|T""v_q
例如: /RJ
yO1
7C
限制以Publishing结尾,使用LIKE '%Publishing' F]yB=
!92e$GJ} ;
限制以A开头:LIKE '[A]%' 6/S.sj~
oYkd%N9P
限制以A开头外:LIKE '[^A]%' U_"!\lI_yg
Fn@`Bi?#q
4、空值判断符例WHERE age IS NULL d j\Z}[
" _2k3
5、逻辑运算符:优先级为NOT、AND、OR y<Q"]H.CkQ
uVn"L:_
(四)查询结果排序 ce\d35x!
RH;ulAD6(~
使用ORDER BY子句对查询返回的结果按一列或多列排序。ORDER BY子句的语法格式为: Dhn7N8(LF!
nUP, Yd
ORDER BY {column_name [ASC|DESC]} [,…n] d=xjLbsZ
^7spXfSAd
其中ASC表示升序,为默认值,DESC为降序。ORDER BY不能按ntext、text和image数据类型进行排 a{T.U-0
7x6M]1F
序。 m}wn+R
T06(Q[)
例如: Q
84t=
D8wf`RUt
SELECT * W]oD(eZ
ae sk.
FROM usertable a
~v$ bNu
G^W0!u,@
ORDER BY age desc,userid ASC 89LD:+p/
X!Z)V)@J8
另外,可以根据表达式进行排序。 {oqbV#/&
gPKf8{#%e
r&
a[?
G(a5@9F
二、联合查询 wu.l-VmGp)
[j0[c9.p[
UNION运算符可以将两个或两个以上上SELECT语句的查询结果集合合并成一个结果集合显示,即执行联 |MZ1j(_
T ?[28|
合查询。UNION的语法格式为: 1 jidBzu<
8D )nM|
select_statement C>+n>bH]L
=o##z5j
K
UNION [ALL] selectstatement jjV'`Vy)
GM%OO)dO}
[UNION [ALL] selectstatement][…n] y8~OkdlN#
9S|sTf
其中selectstatement为待联合的SELECT查询语句。 \ZLi Y
$K^l=X
ALL选项表示将所有行合并到结果集合中。不指定该项时,被联合查询结果集合中的重复行将只保留一 #h[>RtP:
(I}owr 5:
行。 w[-)c6J yE
wN!\$i@E:
联合查询时,查询结果的列标题为第一个查询语句的列标题。因此,要定义列标题必须在第一个查询语 T/'z,,Y
Vn^GJ'^
句中定义。要对联合查询结果排序时,也必须使用第一查询语句中的列名、列标题或者列序号。 8${n}}
1c0'i
在使用UNION 运算符时,应保证每个联合查询语句的选择列表中有相同数量的表达式,并且每个查询选 X,v.1#[
U.<j2Kum
择表达式应具有相同的数据类型,或是可以自动将它们转换为相同的数据类型。在自动转换时,对于数值类 x
7by|G(
ez'NHodwk2
型,系统将低精度的数据类型转换为高精度的数据类型。 #<*.{"T
Nbpn"*L,
在包括多个查询的UNION语句中,其执行顺序是自左至右,使用括号可以改变这一执行顺序。例如: dBXiLrEbs
[~{F(Le
查询1 UNION (查询2 UNION 查询3) 1nAm\/&
'v]0;~\mp>
3}H{4]*%_
ytIPY7E
oVpZR$
MIZdk'.U
三、连接查询 G]ek-[-
j?N<40z
通过连接运算符可以实现多个表查询。连接是关系数据库模型的主要特点,也是它区别于其它类型 7\
_MA!:<
f7_(C0d
数据库管理系统的一个标志。 ?y-^Fq|h
k9x[(
#
在关系数据库管理系统中,表建立时各数据之间的关系不必确定,常把一个实体的所有信息存放在 RTc@`m3 M
@
8H$
一个表中。当检索数据时,通过连接操作查询出存放在多个表中的不同实体的信息。连接操作给用户带 |c/=9Bb
*-9i<@|(U^
来很大的灵活性,他们可以在任何时候增加新的数据类型。为不同实体创建新的表,尔后通过连接进行 q2EDrZ
F=Bdgg9s
查询。 :|W=2(>
U T\4Xk<
连接可以在SELECT 语句的FROM子句或WHERE子句中建立,似是而非在FROM子句中指出连接时有助于 y47N(;vy
_Xd"'cXw
将连接操作与WHERE子句中的搜索条件区分开来。所以,在Transact-SQL中推荐使用这种方法。 \}jA1oy
3*h"B$g!
SQL-92标准所定义的FROM子句的连接语法格式为: O-V|= t
DPT6]pl"y
FROM join_table join_type join_table \\dUp>1=
\78E>(`'
[ON (join_condition)] RzqgN*]lY
-hXKCb4YU
其中join_table指出参与连接操作的表名,连接可以对同一个表操作,也可以对多表操作,对同一 T aS1%(
F{ %*(U
个表操作的连接又称做自连接。 @U_CnhPQq
sE[`x^1'8
join_type 指出连接类型,可分为三种:内连接、外连接和交叉连接。内连接(INNER JOIN)使用比 n2K1X!E$
d=vuy
较运算符进行表间某(些)列数据的比较操作,并列出这些表中与连接条件相匹配的数据行。根据所使用 |}4\Gm
f}bq
的比较方式不同,内连接又分为等值连接、自然连接和不等连接三种。 M^Sa{S*?
D}?p>e|<D
外连接分为左外连接(LEFT OUTER JOIN或LEFT JOIN)、右外连接(RIGHT OUTER JOIN或RIGHT JOIN) 60~;UBm5O
~,}|~
和全外连接(FULL OUTER JOIN或FULL JOIN)三种。与内连接不同的是,外连接不只列出与连接条件相匹 lbAhP+B
Vc9rc}
配的行,而是列出左表(左外连接时)、右表(右外连接时)或两个表(全外连接时)中所有符合搜索条件的 %V>%AP
w0~%,S
数据行。 @R5^J{T
e\V
-L_
交叉连接(CROSS JOIN)没有WHERE 子句,它返回连接表中所有数据行的笛卡尔积,其结果集合中的 \U$:/#1Oe
v[Q)L!J1
数据行数等于第一个表中符合查询条件的数据行数乘以第二个表中符合查询条件的数据行数。 i#la'ICwJ
O >h`
连接操作中的ON (join_condition) 子句指出连接条件,它由被连接表中的列和比较运算符、逻辑 I0+6p8,
]Ucw&B*@
运算符等构成。 CGi;M=xr
;2C
无论哪种连接都不能对text、ntext和image数据类型列进行直接连接,但可以对这三种列进行间接 @-sWXz*W
,>-j Ztm
连接。例如: ~q3O,bb{
OyO]; Yk
SELECT p1.pub_id,p2.pub_id,p1.pr_info Rn?JMM]
;eYG\uKC{
FROM pub_info AS p1 INNER JOIN pub_info AS p2 iN&oSpQ
vaB ql(?'2
ON DATALENGTH(p1.pr_info)=DATALENGTH(p2.pr_info) w^0hVrws=,
1d< b\P0
(一)内连接 3:iEt (iCI
i"<W6
内连接查询操作列出与连接条件匹配的数据行,它使用比较运算符比较被连接列的列值。内连接分 qx ki
Cx2#
0$
三种: tczJk1g}
bA)nWWSg=
1、等值连接:在连接条件中使用等于号(=)运算符比较被连接列的列值,其查询结果中列出被连接 J1G}l5N
AIg4u(j
表中的所有列,包括其中的重复列。 %D4)Bqr
dL$ iTSfz"
2、不等连接: 在连接条件使用除等于运算符以外的其它比较运算符比较被连接的列的列值。这些 ;z4J)qw
8'*x88+
运算符包括>、>=、<=、<、!>、!<和<>。 MDF_Xr-hZ
O(/~cQ
3、自然连接:在连接条件中使用等于(=)运算符比较被连接列的列值,但它使用选择列表指出查询 }&vD(hX
86{>X5 +
结果集合中所包括的列,并删除连接表中的重复列。 j,i9,oF6]
vxZ'-&;t
例,下面使用等值连接列出authors和publishers表中位于同一城市的作者和出版社: *:n7B\.
f]r*;YEc4
SELECT * c]{}|2u
67(s\
FROM authors AS a INNER JOIN publishers AS p }.A]=Ew
!Vyf2xS"
ON a.city=p.city )h,yQ`.
5REFz
又如使用自然连接,在选择列表中删除authors 和publishers 表中重复列(city和state): j,.M!q]
i M !`4
SELECT a.*,p.pub_id,p.pub_name,p.country #uU(G\^T
1b3 a(^^E
FROM authors AS a INNER JOIN publishers AS p DKjiooD
.Exvuo`F
ON a.city=p.city f]i"tqoI
=6~
(二)外连接 ?"Ez
;<M}ZL@m
内连接时,返回查询结果集合中的仅是符合查询条件( WHERE 搜索条件或 HAVING 条件)和连接条件 Ikdj?"+O
Z+v,o1
的行。而采用外连接时,它返回到查询结果集合中的不仅包含符合连接条件的行,而且还包括左表(左外 `^[k8Z(
A;L
]=J
连接时)、右表(右外连接时)或两个边接表(全外连接)中的所有数据行。 N~,Ipf
`0qjaC
如下面使用左外连接将论坛内容和作者信息连接起来: Ca0sm
`$/a-K}
SELECT a.*,b.* FROM luntan LEFT JOIN usertable as b 2jyWkAP'
SZW_V6\t>
ON a.username=b.username VNTbjn]
v7"VH90`!
下面使用全外连接将city表中的所有作者以及user表中的所有作者,以及他们所在的城市: 56)!&MF
+E</A:|}S
SELECT a.*,b.* x[58C +
nz3*s#k\-
FROM city as a FULL OUTER JOIN user as b 3/+kjY/
G Y%5N= u
ON a.username=b.username v^ ^Ibv
bW=q G
(三)交叉连接 i9L]h69r
TO.b-
;
交叉连接不带WHERE 子句,它返回被连接的两个表所有数据行的笛卡尔积,返回到结果集合中的数 yn\c;Z
Ss%Cf6qdWL
据行数等于第一个表中符合查询条件的数据行数乘以第二个表中符合查询条件的数据行数。 g)#?$OhP"
>+J}mo=*
例,titles表中有6类图书,而publishers表中有8家出版社,则下列交叉连接检索到的记录数将等 xeFx!$3
ee?
d?:L
于6*8=48行。 >8"(go+02
FygNWI '
SELECT type,pub_name >pp/4Ia!
8lM=v> Xc
FROM titles CROSS JOIN publishers i6WPf:#wr
*>a=ku:?
ORDER BY type