zoukankan      html  css  js  c++  java
  • 子查询(极客时间)

    子查询

    子查询就是嵌套在查询中的查询, 目的是为了进行更复杂的查询, 同时可以理解查询的过程.

    子查询也分为两种, 一种是关联子查询, 一种是非关联子查询.

    关联子查询与非关联子查询

    子查询的划分是依据了子查询是否执行多次来进行划分的.

    子查询从数据表中查询数据结果, 如果这个数据结果只执行一次, 之后这个数据结果作为主查询的条件进行执行, 这种就是非关联子查询.

    同样, 如果子查询需要执行多次, 即采用循环的方式, 先从外部查询开始, 每次传入子查询进行查询, 之后结果反馈给外部, 这种嵌套方式就是关联子查询.

    举个例子, 创建五张表, player表是球员表, team表是球队表, team_score是球队比赛成绩表, player_score是球员比赛成绩表, height_grades是球员身高对应的等级表.

    如果仅仅学习的话可以自己创建表, 看完之后自己出题自己来做, 没必要非要上面的表, 如需下载请到 https://github.com/cystanford/sql_nba_data 去下载.

    SELECT player_name, height FROM player WHERE height = (SELECT max(height) FROM player); // 查询身高最高的球员信息
    

    上面的子查询就是非关联子查询, 查询最高身高的子查询仅仅执行了一次, 不依赖于外部查询.


    SELECT player_name, height, team_id FROM player AS a WHERE height > (SELECT avg(height) FROM player AS b WHERE a.team_id = b.team_id); // 查询每个球队中大于平均身高的球员信息
    

    这个子查询就是关联子查询了, 因为里面的查询球队队员平均身高依赖于外(主)查询, 需要使用主查询来获取当前队员是哪个球队的.

    EXISTS子查询

    关联子查询通常也和EXISTS一起使用, EXISTS子查询用来判断条件是否满足, 满足的话为TRUE, 不满足的话为FALSE. 现在想查询出场过的球员有哪些, 这个就需要到player_score中去查询全部的球员Id, 有记录表示出场过.

    SELECT player_id, team_id, player_name FROM player WHERE EXISTS (SELECT player_id FROM player_score WHERE player.player_id = player_score.player_id); // EXISTS的关联条件是写在子查询中的
    

    有EXISTS, 自查就有NOT EXISTS, 也就是不存在, 与EXISTS是完全相反的结果.

    与EXISTS有相同含义的还有IN, 这个下面说.

    集合比较子查询

    集合比较子查询的作用是与另一个查询结果集进行比较, 可以再子查询中使用IN, ANY, ALL和SOME操作符.

    现在想查询出场过的球员有哪些, 可以这样写:

    SELECT player_id, team_id, player_name FROM player WHERE player_id in (SELECT player_id FROM player_score WHERE player.player_id = player_score.player_id);  // in查询出场过的球员
    

    哪种效率更好取决于查询表于关联表的数据大小, 查询表达, IN的效率高, 相反, EXISTS的效率高.

    接下来说说ANY和ALL, 这两个通常需要使用比较符, 比较符包括了(>)(=)(<)(>=)(<=)(<>)等.

    要查询比印第安纳步行者(对应的twam_id是1002)中任何一个球员身高高的球员信息, sql如下

    SELECT player_id, player_name, height FROM player WHERE height > ANY (SELECT height FROM player WHERE team_id = 1002); // 主要身高高于子查询中的人一个一个就可以
    SQL: SELECT player_id, player_name, height FROM player WHERE height > ALL (SELECT height FROM player WHERE team_id = 1002); // 身高高于球员中的任意一个球员的身高, 简单的说就是比球队中身高最高的球员还要高.
    
    SELECT p1.* FROM player p1 WHERE p1.height = (SELECT MAX(height) FROM player p2 WHERE p1.team_id = p2.team_id); // 查询每支球队中, 身高最高的球员信息
    

    ANY和ALL关键字必须与一个比较操作符在一起使用, 不适用起不到集合比较的作用, ANY和ALL就没有任何意义.

    子查询作为计算字段

    想查询每支球员的球员数

    SELECT team_name, (SELECT count(*) FROM player WHERE player.team_id = team.team_id) AS player_num FROM team;
    

  • 相关阅读:
    [javaSE] 数组(获取最值)
    [javascript] Promise简单学习使用
    [javaSE] 基本类型(String相关)
    [android] 手机卫士黑名单功能(ListView结合SQLite增删改)
    [PHP] 重回基础(IO流)
    [PHP] 重回基础(Array相关函数)
    [PHP] 重回基础(date函数和strtotime函数)
    [HTML5] Canvas绘制简单图片
    [javaSE] 集合框架(TreeSet)
    [android] 手机卫士黑名单功能(ListView优化)
  • 原文地址:https://www.cnblogs.com/wadmwz/p/11146317.html
Copyright © 2011-2022 走看看