虽然 SELECT 语句的完整语法较复杂,但是其主要的子句可归纳如下:
SELECT select_list
[INTO new_table_name]
FROM table_list
[WHERE search_conditions]
[GROUP BY group_by_list]
[HAVING search_conditions]
[ORDER BY order_list [ASC | DESC] ]
select_list
描述结果集的列。它是一个逗号分隔的表达式列表。每个表达式同时定义格式(数据类型和大小)和结果集列的数据来源。每个选择列表表达式通常是对从中获取数据的源表或视图的列的引用,但也可能是其它表达式,例如常量或 Transact-SQL 函数。在选择列表中使用 * 表达式指定返回源表中的所有列。
INTO new_table_name
指定使用结果集来创建新表。new_table_name 指定新表的名称。
FROM table_list
包含从中检索到结果集数据的表的列表。这些来源可能包括:
- 运行 Microsoft® SQL Server™ 的本地服务器中的基表。
- 本地 SQL Server 中的视图。SQL Server 将一个视图引用内部解析为针对组成视图的基表的多个引用。
-
链接表是可从 SQL Server 进行访问的 OLE DB 数据源中的表。这种访问方式称为分布式查询。通过将 OLE DB 数据源链接为链接服务器或者在 OPENROWSET 或 OPENQUERY 函数中引用数据源,可实现从 SQL Server 访问 OLE DB 数据源。
FROM 子句还可包含联接说明,该说明定义了 SQL Server 用来在表之间进行导航的特定路径。
FROM 子句还用在 DELETE 和 UPDATE 语句中以定义要修改的表。
WHERE search_conditions
WHERE 子句是一个筛选,它定义了源表中的行要满足 SELECT 语句的要求所必须达到的条件。只有符合条件的行才向结果集提供数据。不符合条件的行中的数据不会被使用。
WHERE 子句还用在 DELETE 和 UPDATE 语句中以定义目标表中要修改的行。
GROUP BY group_by_list
GROUP BY 子句根据 group_by_list 列中的值将结果集分成组。例如,Northwind Orders 表在 ShipVia 中有三个值。GROUP BY ShipVia 子句将结果集分成三组,每组对应于 ShipVia 的一个值。
HAVING search_conditions
HAVING 子句是应用于结果集的附加筛选。逻辑上讲,HAVING 子句从中间结果集对行进行筛选,这些中间结果集是用 SELECT 语句中的 FROM、WHERE 或 GROUP BY 子句创建的。HAVING 子句通常与 GROUP BY 子句一起使用,尽管 HAVING 子句前面不必有 GROUP BY 子句。
ORDER BY order_list [ ASC | DESC ]
ORDER BY 子句定义结果集中的行排列的顺序。order_list 指定组成排序列表的结果集的列。ASC 和 DESC 关键字用于指定行是按升序还是按降序排序。
ORDER BY 之所以重要,是因为关系理论规定除非已经指定 ORDER BY,否则不能假设结果集中的行带有任何序列。如果结果集行的顺序对于 SELECT 语句来说很重要,那么在该语句中就必须使用 ORDER BY 子句。
必须按照正确的顺序指定 SELECT 语句中的子句。
对数据库对象的每个引用都不得引起歧义。下列情况可能会导致多义性:
-
在系统中,可能有多个对象带有相同的名称。例如,User1 和 User2 可能都指定了一个名为 TableX 的表。若要解析多义性并且指定 TableX 为 User1 所有,请至少使用用户 ID 来限定表的名称:
SELECT * FROM User1.TableX
-
在执行 SELECT 语句时,对象所驻留的数据库不一定总是当前数据库。若要确保总是使用正确的对象,则不论当前数据库是如何设置的,均应使用数据库和所有者来限定对象名称:
SELECT * FROM Northwind.dbo.Shippers
-
在 FROM 子句中所指定的表和视图可能有相同的列名。外键很可能具有和相关主键相同的列名。若要解析重复名称之间的多义性,必须使用表或视图名称来限定列名:
SELECT DISTINCT Customers.CustomerID, Customers.CompanyName FROM Customers JOIN Orders ON ( Customers.CustomerID = Orders.CustomerID) WHERE Orders.ShippedDate > 'May 1 1998'
当必须完全限定表和视图名称本身时,上述语法会变得很烦琐。通过在 FROM 子句中使用 AS 关键字为表指派一个相关名称(也称为范围变量或别名)即可解决此问题。只能在 FROM 子句中定义完全合法的表或视图名称。然后所有其它表或视图引用都可使用此相关名称。在前一个示例中应用相关名称并且完全限定表,会有如下的 SELECT 语句:
SELECT DISTINCT Cst.CustomerID, Cst.CompanyName FROM Northwind.dbo.Customers AS Cst JOIN Northwind.dbo.Orders AS Ord ON ( Cst.CustomerID = Ord.CustomerID) WHERE Ord.ShippedDate > 'May 1 1998'