sql server关键字详解大全(图文)

所属分类: 数据库 / MsSql 阅读数: 281
收藏 0 赞 0 分享

下面把sqlserver中cross apply和outer apply关键字具体介绍展示如下:

1.CROSS APPLY 和OUTER APPLY

MSDN解释如下(个人理解不是很清晰):

使用 APPLY 运算符可以为实现查询操作的外部表表达式返回的每个行调用表值函数。表值函数作为右输入,外部表表达式作为左输入。

通过对右输入求值来获得左输入每一行的计算结果,生成的行被组合起来作为最终输出。

APPLY 运算符生成的列的列表是左输入中的列集,后跟右输入返回的列的列表。

APPLY 有两种形式:

CROSS APPLY 和 OUTER APPLY。

CROSS APPLY 仅返回外部表中通过表值函数生成结果集的行。

OUTER APPLY 既返回生成结果集的行,也返回不生成结果集的行,其中表值函数生成的列中的值为 NULL。

网上搜集的解释如下(个人感觉好理解):

SQL Server数据库操作中,在2005以上的版本新增加了一个APPLY表运算符的功能。新增的APPLY表运算符把右表表达式应用到左表表达式中的每一行。

它不像JOIN那样先计算哪个表表达式都可以,APPLY必须先逻辑地计算左表达式。这种计算输入的逻辑顺序允许把右表达式关联到左表表达式。

APPLY有两种形式,一个是OUTER APPLY,一个是CROSS APPLY,区别在于指定OUTER,意味着结果集中将包含使右表表达式为空的左表表达式中的行,而指定CROSS,则相反,结果集中不包含使右表表达式为空的左表表达式中的行。

注意:若要使用 APPLY,数据库兼容级别必须为 90。

下面我们做个例子:

比如有个类别表(Category)内容如下:

 

还有个类别明细表(CategoryDetail)内容如下:

下面我们来看看OUTER APPLY 的查询结果:

 SELECT *
 FROM dbo.Category a
   OUTER APPLY ( SELECT *
      FROM  dbo.CategoryDetail b
      WHERE  b.CategoryId = a.Id
      ) AS c ;

由上图可看出OUTER APPLY把左表中的信息查出后把右表中的信息也关联出来了,当然当右表的信息为空(NULL)时,OUTER APPLY也会在结果集中显示出来.

接下来我们看下CROSS APPLY的查询结果:

 SELECT *
 FROM dbo.Category a
   CROSS APPLY ( SELECT *
      FROM  dbo.CategoryDetail b
      WHERE  b.CategoryId = a.Id
      ) AS c ;

根据这图和上面的比较可看出,这个返回结果只有两个,Category 表中的Tiger的信息没有带出来,因为在CategoryDetail 表中没有对应的明细.

由以上信息可得出,OUTER APPLY 就相当于数学中的并集,而CROSS APPLY相当于数学中的交集,关于交集与并集的介绍如下:

并集为下图中的所有红色部分,即为A和B的全部:

交集为下图中的红色部分,也就是A和B相交的部分:

2.OUTER APPLY 和LEFT JOIN

LEFT JOIN 关键字会从左表 (Category) 那里返回所有的行,即使在右表 (CategoryDetail) 中没有匹配的行。

注释:在某些数据库中, LEFT JOIN 称为 LEFT OUTER JOIN。

下面我们来看看LEFT JOIN 的查询结果(还是1.CROSS APPLY 和 OUTER APPLY中的例子):

 SELECT *
 FROM dbo.Category a
   LEFT JOIN dbo.CategoryDetail b ON b.CategoryId = a.Id ;

LEFT JOIN 关键字会从左表 (Category) 那里返回所有的行,即使在右表 (CategoryDetail) 中没有匹配的行。效果和OUTER APPLY 一样。

OUTER APPLY 和 LEFT JOIN 的主要区别为:

  一个LEFT JOIN 关键字只能JOIN 一个表,不能解决一个复杂的SELECT 语句,或者函数方法等。

  一个OUTER APPLY 关键字可以包含一个独立的复杂的SELECT 语句,或者其他函数方法等。

OUTER APPLY 和 LEFT JOIN 性能的区别:

  通过本文总结可知LEFT JOIN和OUTER APPLY性能比较的总结可知 LEFT JOIN 要比 OUTER APPLY 性能要快。所以建议能用LEFT JOIN的尽量不要用OUTER APPLY。

附注:

附Category 表和CategoryDetail 表的结果及插入数据的脚本:

CREATE TABLE [dbo].[CategoryDetail](
  [Id] [int] IDENTITY(,) NOT NULL,
  [CategoryId] [int] NULL,
  [Cry] [varchar]() NULL,
 CONSTRAINT [PK_CategoryDetail] PRIMARY KEY CLUSTERED 
 (
  [Id] ASC
 )WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
 ) ON [PRIMARY]
 GO
 SET ANSI_PADDING OFF
 GO
 SET IDENTITY_INSERT [dbo].[CategoryDetail] ON
 INSERT [dbo].[CategoryDetail] ([Id], [CategoryId], [Cry]) VALUES (, , N'喵')
 INSERT [dbo].[CategoryDetail] ([Id], [CategoryId], [Cry]) VALUES (, , N'汪')
 SET IDENTITY_INSERT [dbo].[CategoryDetail] OFF
 /****** Object: Table [dbo].[Category] Script Date: // :: ******/
 SET ANSI_NULLS ON
 GO
 SET QUOTED_IDENTIFIER ON
 GO
 SET ANSI_PADDING ON
 GO
 CREATE TABLE [dbo].[Category](
  [Id] [int] IDENTITY(,) NOT NULL,
  [Name] [varchar]() NULL,
 CONSTRAINT [PK_Category] PRIMARY KEY CLUSTERED 
 (
  [Id] ASC
 )WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
 ) ON [PRIMARY]
 GO
 SET ANSI_PADDING OFF
 GO
 SET IDENTITY_INSERT [dbo].[Category] ON
 INSERT [dbo].[Category] ([Id], [Name]) VALUES (, N'Cat')
 INSERT [dbo].[Category] ([Id], [Name]) VALUES (, N'Dog')
 INSERT [dbo].[Category] ([Id], [Name]) VALUES (, N'Tiger')
 SET IDENTITY_INSERT [dbo].[Category] OFF

以上内容就是本文的全部所示,希望大家喜欢。

更多精彩内容其他人还在看

SQL 提权 常用命令

SQL 提权 常用命令,大家可以考虑下将sqlserver的服务运行权限设置为普通用户,即可防止下面的提权。
收藏 0 赞 0 分享

数据转换冲突及转换过程中大对象的处理

数据转换冲突及转换过程中大对象的处理方法,大家可以参考下。
收藏 0 赞 0 分享

SQLServer 数据库开发顶级技巧

无论你的专业水平如何,从其他IT专家那里学习新的技巧与最佳实践常常都是有益的。本文包含了我遇到过的SQL Server开发的高级技巧。希望其中的一些技巧能够对您的数据库开发及管理工作有所帮助。
收藏 0 赞 0 分享

远程连接SQLSERVER 2000服务器方法

需求如下:需要远程连接外地的SQL Server 2000服务器。
收藏 0 赞 0 分享

SQLserver2000 企业版 出现"进程51发生了严重的异常"错误的处理方法

SQL2000 企业版 出现“进程51发生了严重的异常”错误的解决方法,利用了微软官方的工具。
收藏 0 赞 0 分享

SQLServer 触发器 数据库进行数据备份

首先,你需要建立测试数据表,一个用于插入数据:test3,另外一个作为备份:test3_bak
收藏 0 赞 0 分享

SQLServer 数据库备份过程中经常遇到的九种情况

SQLServer 数据库备份过程中经常遇到各种问题,大家可以参照下面的问题,来分析下,快速的解决问题。
收藏 0 赞 0 分享

SQL 截取字符串应用代码

字符串截取函数,只限单字节字符使用(对于中文的截取时遇上奇数长度是会出现乱码,需另行处理),本函数可截取字符串指定范围内的字符。
收藏 0 赞 0 分享

除MSSQL数据库text字段中恶意脚本的删方法

删除MSSQL数据库text字段的替换处理示例--全表替换,看到有人提问,所以整理了一个好久以前的处理方法,以供大家参考
收藏 0 赞 0 分享

sql 普通行列转换

说明:普通行列转换(version 1.0)仅针对sql server 2000提供静态和动态写法,version 2.0增加sql server 2005的有关写法。
收藏 0 赞 0 分享
查看更多