专栏首页james大数据架构你真的会玩SQL吗?表表达式,排名函数

你真的会玩SQL吗?表表达式,排名函数

你真的会玩SQL吗?系列目录

你真的会玩SQL吗?之逻辑查询处理阶段

你真的会玩SQL吗?和平大使 内连接、外连接

你真的会玩SQL吗?三范式、数据完整性

你真的会玩SQL吗?查询指定节点及其所有父节点的方法

你真的会玩SQL吗?让人晕头转向的三值逻辑

你真的会玩SQL吗?EXISTS和IN之间的区别

你真的会玩SQL吗?无处不在的子查询

你真的会玩SQL吗?Case也疯狂

你真的会玩SQL吗?表表达式,排名函数

你真的会玩SQL吗?简单的 数据修改

你真的会玩SQL吗?你所不知道的 数据聚合

你真的会玩SQL吗?透视转换的艺术

你真的会玩SQL吗?冷落的Top和Apply

你真的会玩SQL吗?实用函数方法汇总

你真的会玩SQL吗?玩爆你的数据报表之存储过程编写(上)

你真的会玩SQL吗?玩爆你的数据报表之存储过程编写(下)

这次讲的有些可能是经常用但不会注意到,所以来统一总结一下用法。

我们往往需要临时存储某些结果集。除了用临时表和表变量,还可以使用公用表表达式的方法。

表表达式

    1. 期待单个值的地方可以使用标量子查询
    2. 期待多个值的地方可以使用多值子查询
    3. 在期待出现表的地方可用表值子查询表表达式

1.派生表

是从查询表达式派生出虚拟结果表的表表达式,派生表的存在范围只是外部查询。

使用形式:from 派生表 as 派生表列名

规则:

    1. 所有列必须有名称
    2. 列名必须唯一
    3. 不允许使用order by(除非指定了top)

不同于标量和多值子查询,派生表不能是相关的,它必须是独立的。

2.公用表表达式(CTE)

非递归公用表表达式(CTE)是查询结果仅仅一次性返回一个结果集用于外部查询调用。

WITH CTE_Test
  AS
  (
      SELECT * FROM Person_1
  )
  SELECT * FROM CTE_Test AS a  --第一次引用
  INNER JOIN  CTE_Test AS b    --第二次引用
  ON a.Id = b.Id
  ORDER BY a.Id DESC
--SELECT * FROM CTE_Test 再查询一次会报错

递归公用表达式

来引用他人的一个示例:

先建一张表栏目表如下,栏目Id,栏目名称,栏目的父栏目

现在使用CTE查询其每个栏目是第几层栏目的代码如下:

WITH COL_CTE(Id,Name,ParentId,tLevel )
AS
(
    --基本语句
    SELECT Id,Name,ParentId,0 AS tLevel FROM Col
    WHERE ParentId = 0
    UNION ALL
    --递归语句
    SELECT c.Id,c.Name,c.ParentId,ce.tLevel+1 AS tLevel FROM COL as c 
    INNER JOIN COL_CTE AS ce   --递归调用
    ON c.ParentId = ce.Id
)

SELECT * FROM COL_CTE

结果:

0表示顶级栏目。1就是1级栏目

排名函数

四个排名函数:

  1.row_number

  2.rank

  3.dense_rank

  4.ntile

排名函数order by子句是必需的。我们这里不讲定义,直接讲实例用法。

利用row_number生成连续行号

SELECT  empid ,
        qty ,
        ROW_NUMBER() OVER ( ORDER BY qty ) AS rownum
FROM    sales
ORDER BY qty

小的分组范围内排序通过PARTITION BY选项来重新排序,给数据分区或者数据区域唯一的递增序号

如:LastName以‘A’开头的作为第一组,在这个组内进行排序。以‘B’开头的作为第二组,在这个组内排序。以‘C’开头的作为第三组,在这个组内进行排序,如此等等

select
ROW_NUMBER() over(PARTITION by substring(LastName,1,1) order by LastName) as RowNum,
FirstName+' '+ LastName as FullName
from HumanResources.vEmployee

结果

假设LastName以‘A’开头的是男子组,这个组有共有三个人,Kim Abercrombie是冠军,Jay Adams是亚军,Nancy Anderson是季军。假设LastName以‘B’开头的是女子组,这个组只有一个人Bryan Baker,无论如何她都是冠军。等等如此类推。这样一眼就能看出他们的小组名次了。

RANK

果有同时撞线的情况发生应该怎么计名次呢?例如A第一个撞线,B和C同时第二个撞线,D第三个撞线,如果我们想把D的名次计为第4名应该怎么处理呢?就是说不计顺序名次,只计人数。这时就可以使用RANK函数了。

在order by子句中定义的列上,如果返回一行数据与另一行具有相同的值,rank函数将给这些行赋予相同的排名数值。在排名的过程中,保持一个内部计数值,当值有所改变时,排名序号将有一个跳跃。

SELECT  ROW_NUMBER() OVER ( ORDER BY Department ) AS RowNum ,
        RANK() OVER ( ORDER BY Department ) AS Ranking ,
        FirstName + ' ' + LastName AS FullName ,
        Department
FROM    HumanResources.vEmployeeDepartment
ORDER BY RowNum

rank()函数右面也要跟上一个over子句。为了看到效果我们以Department作为排序字段,可以看到RowNum作为升序连续排名,Ranking作为计同排名,当Department的值相同时,Ranking中的值保持不变,当Ranking中的值发生变化时,Ranking列中的值将跳跃到正确的排名数值。来看结果:

从这个结果中我们可以说这次马拉松赛跑的排名是:Tengiz Kharatishvili,Zainal Arifin,Sean Chai,Karen Berge,Chris Norred并列第1,Michael Sullivan,Sharon Salavaria,Roberto Tamburello,Gail Erickson,Jossef Goldberg并列第6,如此等等。

DENSE_RANK

A第一个撞线,B和C同时第二个撞线,D第三个撞线,如果我们想把B和C的名次计位第2名,D的名次计为第3名应该怎么处理呢?就是说考虑并列名次。这里使用DENSE_RANK函数

SELECT  ROW_NUMBER() OVER ( ORDER BY Department ) AS RowNum ,
        DENSE_RANK() OVER ( ORDER BY Department ) AS Ranking ,
        FirstName + ' ' + LastName AS FullName ,
        Department
FROM    HumanResources.vEmployeeDepartment
ORDER BY RowNum

结果

按照这个结果,我们可以说这次马拉松赛跑的排名是:Tengiz Kharatishvili,Zainal Arifin,Sean Chai,Karen Berge,Chris Norred并列第1,Michael Sullivan,Sharon Salavaria,Roberto Tamburello,Gail Erickson,Jossef Goldberg,Terri Duffy并列第2,等等。

NTILE

梭罗是铅笔的发明者,不过他没有申请专利。据说他天赋异禀,在父亲的铅笔厂里面打包铅笔的时候,从一堆铅笔里面抓取一把,每次都能精确地抓到一打12支。他在森林中目测两颗树之间的距离,和护林员用卷尺测量的结果相差无几。现在如果我们想从一张表中抓取多比数据,每一笔都是相同的数目,并且标明第几组该怎么办呢?NTILE函数提供了这个功能。

SELECT  NTILE(30) OVER ( ORDER BY Department ) AS NTiles ,
        FirstName + ' ' + LastName AS FullName ,
        Department
FROM    HumanResources.vEmployeeDepartment

现在我们要抓取30个组的数据,并保证尽可能的保证每组数目相同

这个视图中共290条数据,290/30=9.7约等于10,所以每组10条数据,如图每一条数据都有一个组号。这个结果要比索罗精确。

练习

用CTE删除重复数据

创建一个用于测试的表,并在该表里插入几条数据(包括重复的数据)

/* Create Table with 7 records- 3 are duplicate records*/
CREATE TABLE DeleteDuplicateTest ( Col1 INT, Col2 INT )
INSERT  INTO DeleteDuplicateTest
        SELECT  1 ,
                1
        UNION ALL
        SELECT  1 ,
                1 --duplicate
        UNION ALL
        SELECT  1 ,
                1 --duplicate
        UNION ALL
        SELECT  1 ,
                2
        UNION ALL
        SELECT  1 ,
                2 --duplicate
        UNION ALL
        SELECT  1 ,
                3
        UNION ALL
        SELECT  1 ,
                4
GO

用CTE删除重复数据4条惟一的记录

参考SQL

WITH    CTE ( COl1, Col2, DuplicateCount )
          AS ( SELECT   COl1 ,
                        Col2 ,
                        ROW_NUMBER() OVER ( PARTITION BY COl1, Col2 ORDER BY Col1 ) AS DuplicateCount
               FROM     DELETEDUPLICATETEST
             )
    DELETE  FROM CTE
    WHERE   DuplicateCount > 1
GO

/*用SQL SERVER 的CTE,它将重新生成一个相同的但附加了一行编号的表。在此方案中,我们有Col1,Col2以及包含这个两列重复数的列,对于不同的查询,这个重复数的列可能有不同的值。另一点需要注意的是,一旦CTE被创建,DELETE语句就可以被运行了。这里我们设置一个条件——当我们读取到的记录大于一条(即有重复数据),我们删除除了第一条的所有其他(这里可能有点绕,简单的话就是保留一条重复的记录)*/

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • 你真的会玩SQL吗?透视转换的艺术

    你真的会玩SQL吗?系列目录 你真的会玩SQL吗?之逻辑查询处理阶段 你真的会玩SQL吗?和平大使 内连接、外连接 你真的会玩SQL吗?三范式、数据完整性 你真...

    欢醉
  • 你真的会玩SQL吗?简单的数据修改

    你真的会玩SQL吗?系列目录 你真的会玩SQL吗?之逻辑查询处理阶段 你真的会玩SQL吗?和平大使 内连接、外连接 你真的会玩SQL吗?三范式、数据完整性 你真...

    欢醉
  • NET实现微信公共平台上传下载多媒体文件

          举个例子,有人对着我们的公共微信号拍个照片发送过来,然后我们处理这个照片,比如进行ocr识别字(随后就会降到这个例子),或者人脸识别,或者拍照取证等...

    欢醉
  • 《统计学习方法》读书笔记

    【第1章】 统计学习方法概论 【第2章】 感知机 【第3章】 k 近邻法 【第4章】 朴素贝叶斯法 【第5章】 决策树 【第6章】 逻辑斯谛回归与最大...

    echobingo
  • 8.4 CG 标准函数库

    和 C 的标准函数库类似,Cg 提供了一系列内建的标准函数。这些函数用于执行数学上的通用计算或通用算法(纹理映射等),例如,需要求取入射光线的反射光线方向向量可...

    代码咖啡
  • Python小世界:匿名函数、高阶函数、

    木子本人搞起Python已有多年,一直觉得什么都会,但是有时候实操起来,才觉得很多底层基础的知识都没有彻底的灵活掌握。 另外,网上关于Python基础知识的各...

    py3study
  • 什么是机器学习

    1. 引言(Introduction) 1.1 Welcome 1.2 什么是机器学习(What is Machine Learning) 1.3 监督学...

    用户2188327
  • R语言读入数据库的中英名词互译测试并计分脚本(考试用)

        1. 分子生物学中英文.csv,输入文件,两列,以tab键分隔的txt文本,没有列名

    用户1680321
  • Python黑帽编程2.5 函数

    写了几节的基础知识,真心感觉有点力不从心。这块的内容说实话,看文档是最好的方式,本人的写作水平,真的是找不出更好的写法,头疼。简单带过和没写一样,写详细了和本系...

    用户1631416
  • 必懂的NoSQL理论-Map-Reduce(上)

    本文主要内容:基本的Map-Reduce Map-Reduce 基本原理 面向聚合的数据库能够兴起很大一部分原因是由于集群的增长。数据库运行在集群环境中意...

    ImportSource

扫码关注云+社区

领取腾讯云代金券