高阶SQL语句(二)
一 子查询
也被称作内查询或者嵌套查询,是指在一个查询语句里面还嵌套着另一个查询语 句。子查询语句
是先于主查询语句被执行的,其结果作为外层的条件返回给主查询进行下一 步的查询过滤。
①子语句可以与主语句所查询的表相同,也可以是不同表
②子语句中的sql语句是为了,最后过滤出一个结果集,用于主语句的判断条件
③ in: 将主表和子表关联/连接的语法
环境准备:
mysql> use kgc_ky35;
Reading table information for completion of table and column names
You can turn off this feature to get a quicker startup with -ADatabase changed
mysql> show tables;
+--------------------+
| Tables_in_kgc_ky35 |
+--------------------+
| HP |
| test01 |
| test02 |
| test03 |
+--------------------+
4 rows in set (0.00 sec)mysql> select * from HP;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)
in:查询已知数据记录
IN 用来判断某个值是否在给定的结果集中,通常结合子查询来使用
mysql> create table football (id int);
Query OK, 0 rows affected (0.01 sec)mysql> insert into football values(1),(2),(3);
Query OK, 3 rows affected (0.01 sec)
Records: 3 Duplicates: 0 Warnings: 0mysql> select * from football;
+------+
| id |
+------+
| 1 |
| 2 |
| 3 |
+------+
3 rows in set (0.00 sec)mysql> select id,name,score from HP where id in (select id from football);
+------+------+-------+
| id | name | score |
+------+------+-------+
| 1 | hz | 90.00 |
| 2 | mdq | 80.00 |
| 2 | cx | 60.00 |
+------+------+-------+
3 rows in set (0.00 sec)#先查询football数据表中的id字段列 将查询到的结果id字段列作为一个已知的值的数据记录;再根据已知的值的数据记录查询football数据表中id,name,score字段列
多表查询举例:
mysql> select name,score from HP where id in (select id from football where score>60);
+------+-------+
| name | score |
+------+-------+
| hz | 90.00 |
| mdq | 80.00 |
+------+-------+
2 rows in set (0.00 sec)
mysql> select name,score from HP where id in (select id from HP where score>70);
+------+-------+
| name | score |
+------+-------+
| hz | 90.00 |
| mdq | 80.00 |
| cx | 60.00 |
+------+-------+
3 rows in set (0.00 sec)
多表查询
子查询不仅可以在 SELECT 语句中使用,在 INERT、UPDATE、DELETE 中也同样适用。在嵌套
的时候,子查询内部还可以再次嵌套新的子查询,也就是说可以多层嵌套。
①语法
IN 用来判断某个值是否在给定的结果集中,通常结合子查询来使用
<表达式> [NOT] IN <子查询>
当表达式与子查询返回的结果集中的某个值相等时,返回 TRUE,否则返回 FALSE。 若启用了 NOT 关键字,则返回值相反。
注意:子查询只能返回一列数据,如果需 求比较复杂,一列解决不了问题,可以使用多层嵌套的
方式来应对。 多数情况下,子查询都是与 SELECT 语句一起使用的
表示 先匹配出member表内的id字段为基础匹配的结果集(2,3),然后再执行主语句,以主语句的id 为基础 进行where 条件判断/过滤
②插入
mysql> select * from test03;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
+------+------+-------+---------+-------+
2 rows in set (0.00 sec)mysql> delete from test03;
Query OK, 2 rows affected (0.01 sec)mysql> insert into test03 select * from test01 where id in ( select id from HP);
Query OK, 3 rows affected (0.00 sec)
Records: 3 Duplicates: 0 Warnings: 0mysql> select * from test03;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)
③修改数据:
update语句也可以使用子查询。update 内的子查询,在 set 更新内容时,可以是单独的一
列,也可以是多列。
mysql> select * from test03;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)mysql> update test03 set score=44 where id in (select id from HP where id=1);
Query OK, 1 row affected (0.01 sec)
Rows matched: 1 Changed: 1 Warnings: 0mysql> select * from test03;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 44.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)
④删除:
在 IN 前面还可以添加 NOT,其作用与IN相反,表示否定(即不在子查询的结果集里面)
DELETE 也适用于子查询,
环境准备:
mysql> show tables;
+--------------------+
| Tables_in_kgc_ky35 |
+--------------------+
| HP |
| football |
| jinjin |
| kangkang |
| test01 |
| test02 |
| test03 |
| test1 |
| test2 |
| v_HP |
| v_hc |
| v_score |
+--------------------+
12 rows in set (0.00 sec)mysql> select * from test02;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)
mysql> delete from test02 where id in (select id from test02 where score > 85);
ERROR 1093 (HY000): You can't specify target table 'test02' for update in FROM clause
mysql> select * from test02 where score > 85;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
+------+------+-------+---------+-------+
1 row in set (0.00 sec)mysql> delete from test02 where id in (select id from test02 where score > 85);
ERROR 1093 (HY000): You can't specify target table 'test02' for update in FROM clause
mysql> select * from test01;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)多表删除,至少两个表,且有相同的部分才行mysql> update test01 set score=96,hobby=2 where id=1;
Query OK, 1 row affected (0.00 sec)
Rows matched: 1 Changed: 1 Warnings: 0mysql> select * from test01;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 96.00 | tianye | 2 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.01 sec)mysql> delete from test02 where id in (select id from test01 where score > 85);
Query OK, 1 row affected (0.01 sec)
结果:
mysql> select * from test01;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 96.00 | tianye | 2 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)mysql> select * from test02;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
2 rows in set (0.00 sec)
⑤exists
主要用于判断子查询的结果集是否为空。如果不为空, 则返回 TRUE;反之,则返回 FALSE;
mysql> select * from test02;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)mysql> select sum(score) from test02 where exists(select id from test02 where score <80);
+------------+
| sum(score) |
+------------+
| 230.00 |
+------------+
1 row in set (0.00 sec)mysql> select sum(score) from test02 where exists(select id from test02 where score >90);
+------------+
| sum(score) |
+------------+
| NULL |
+------------+
1 row in set (0.00 sec)
⑥not取反
在 IN 前面还可以添加 NOT,其作用与IN相反,表示否定(即不在子查询的结果集里面)
mysql> select * from test01;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 96.00 | tianye | 2 |
| 2 | mdq | 80.00 | renduo | 3 |
| 3 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)mysql> select * from test02;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 4 | jhg | 85.00 | nanjing | 4 |
| 2 | mdq | 80.00 | renduo | 3 |
| 3 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)
mysql> select * from test01 where id not in(select id from test02 where id);
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 96.00 | tianye | 2 |
+------+------+-------+---------+-------+
1 row in set (0.00 sec)
⑦别名as
查询info表id,name 字段;select id,name from info;
可以查看到info表的内容
将结果集做为一张表进行查询的时候,我们也需要用到别名,示例:
需求:从info表中的id和name字段的内容做为"内容" 输出id的部分
mysql> select * from test02;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)mysql> select id ,name from HP;
+------+------+
| id | name |
+------+------+
| 1 | hz |
| 2 | mdq |
| 2 | cx |
+------+------+
3 rows in set (0.00 sec)mysql> select id ,name from (select id,name from HP) a;
+------+------+
| id | name |
+------+------+
| 1 | hz |
| 2 | mdq |
| 2 | cx |
+------+------+
3 rows in set (0.01 sec)
二 视图=优化操作+安全方案
数据库中的虚拟表,这张虚拟表中不包含真实数据,只是做了真实数据的映射
视图可以理解为镜花水月/倒影,动态保存结果集(数据)
作用场景:
针对不同的人(权限身份),提供不同结果集的“表”(以表格的形式展示)
展示的部分是info表
展示的一张或多张表
功能:
简化查询结果集、灵活查询、可以针对不同用户呈现不同结果集、相对有更高的安全性
本质而言视图是一种select(结果集的呈现)
视图适合于多表连接浏览时使用!不适合增、删、改
而存储过程适合于使用较频繁的SQL语句,这样可以提高执行效率!
视图和表的区别
① 视图是已经编译好的sql语句。而表不是
② 视图没有实际的物理记录。而表有。
show table status\G
③ 表只用物理空间而视图不占用物理空间,视图只是逻辑概念的存在,表可以及时对它进行修改,但视图只能有创建的语句来修改
④ 视图是查看数据表的一种方法,可以查询数据表中某些字段构成的数据,只是一些SQL语句的集合。从安全的角度说,视图可以不给用户接触数据表,从而不知道表结构。
⑤ 表属于全局模式中的表,是实表;视图属于局部模式的表,是虚表。
⑥ 视图的建立和删除只影响视图本身,不影响对应的基本表。(但是更新视图数据,是会影响到基本表的)
联系:
视图(view)是在基本表之上建立的表,它的结构(即所定义的列)和内容(即所有数据行)都来自基本
表,它依据基本表存在而存在。一个视图可以对应一个基本表,也可以对应多个基本表。视图是基
本表的抽象和在逻辑意义上建立的新关系。
单表演练
mysql> desc test02;
+---------+--------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+---------+--------------+------+-----+---------+-------+
| id | int(10) | YES | | NULL | |
| name | varchar(16) | NO | | NULL | |
| score | decimal(5,2) | YES | | NULL | |
| address | varchar(40) | YES | | NULL | |
| hobby | int(8) | YES | | NULL | |
+---------+--------------+------+-----+---------+-------+
5 rows in set (0.00 sec)mysql> create view v_score as select * from test02 where score>=90;
Query OK, 0 rows affected (0.01 sec)
#创建视图mysql> show table status\G #查看表状态
*************************** 1. row ***************************Name: HPEngine: MyISAMVersion: 10Row_format: DynamicRows: 3Avg_row_length: 28Data_length: 84
Max_data_length: 281474976710655Index_length: 2048Data_free: 0Auto_increment: NULLCreate_time: 2024-03-26 15:53:59Update_time: 2024-03-26 15:58:45Check_time: NULLCollation: utf8_general_ciChecksum: NULLCreate_options: Comment:
*************************** 2. row ***************************
mysql> desc v_score; #查看视图与源表结构
+---------+--------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+---------+--------------+------+-----+---------+-------+
| id | int(10) | YES | | NULL | |
| name | varchar(16) | NO | | NULL | |
| score | decimal(5,2) | YES | | NULL | |
| address | varchar(40) | YES | | NULL | |
| hobby | int(8) | YES | | NULL | |
+---------+--------------+------+-----+---------+-------+
5 rows in set (0.00 sec)
多表视图创立
相同的名字或相同的值都可以导入里面
mysql> create table kangkang(id int,name varchar(15),age varchar(16));
Query OK, 0 rows affected (0.00 sec)mysql> select * from HP;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)mysql> insert into kangkang values(1,'liubei',56);
Query OK, 1 row affected (0.00 sec)mysql> insert into kangkang values(2,'lubu',40);
Query OK, 1 row affected (0.00 sec)mysql> insert into kangkang values(3,'jiaxu',75);
Query OK, 1 row affected (0.00 sec)mysql> insert into kangkang values(4,'mazhong',28);
Query OK, 1 row affected (0.01 sec)mysql> select * from kangkang;
+------+---------+------+
| id | name | age |
+------+---------+------+
| 1 | liubei | 56 |
| 2 | lubu | 40 |
| 3 | jiaxu | 75 |
| 4 | mazhong | 28 |
+------+---------+------+
4 rows in set (0.00 sec)
4 rows in set (0.00 sec)mysql> create view v_HP(id,name,score,age) as select k.id,k.name,k.score,s.age from HP k,kangkang s where k.name=s.name;
Query OK, 0 rows affected (0.01 sec)mysql> select * from v_HP;
Empty set (0.01 sec)
#因为名字不相同,需要改一下,
mysql> create view v_hc(id,name,score,age) as select k.id,k.name,k.score,s.age from HP k,kangkang s where k.name=s.name;
Query OK, 0 rows affected (0.01 sec)
# v_hc,可任意取名,
mysql> select * from v_hc;
+------+------+-------+------+
| id | name | score | age |
+------+------+-------+------+
| 2 | cx | 60.00 | 28 |
+------+------+-------+------+
修改表数据
修改表不能修改以函数、复合函数方式计算出来的字段
mysql> select * from HP;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)
mysql> update HP set score='77' where name='cx';
Query OK, 1 row affected (0.00 sec)
Rows matched: 1 Changed: 1 Warnings: 0mysql> select * from v_HP;
+------+------+-------+------+
| id | name | score | age |
+------+------+-------+------+
| 2 | cx | 77.00 | 28 |
+------+------+-------+------+
修改视图
修改视图时也修改表的数据
mysql> select * from v_HP;
+------+------+-------+------+
| id | name | score | age |
+------+------+-------+------+
| 2 | cx | 77.00 | 28 |
+------+------+-------+------+
1 row in set (0.00 sec)mysql> update v_HP set score='98' where name='cx';
Query OK, 1 row affected (0.01 sec)
Rows matched: 1 Changed: 1 Warnings: 0mysql> select * from v_HP;
+------+------+-------+------+
| id | name | score | age |
+------+------+-------+------+
| 2 | cx | 98.00 | 28 |
+------+------+-------+------+
1 row in set (0.00 sec)mysql> select * from HP;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 85.00 | renduo | 3 |
| 2 | cx | 98.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)
三 NULL 值--缺失
在 SQL 语句使用过程中,经常会碰到 NULL 这几个字符。通常使用 NULL 来表示缺失 的值,也就是在表中该字段是没有值的。如果在创建表时,限制某些字段不为空,则可以使用 NOT NULL 关键字,不使用则默认可以为空。在向表内插入记录或者更新记录时,如果该字段没有 NOT NULL 并且没有值,这时候新记录的该字段将被保存为 NULL。需要注意 的是,NULL 值与数字 0 或者空白(spaces)的字段是不同的,值为 NULL 的字段是没有 值的。在 SQL 语句中,使用 IS NULL 可以判断表内的某个字段是不是 NULL 值,相反的用 IS NOT NULL 可以判断不是 NULL 值。
null值与空值的区别(空气与真空)
空值长度为0,不占空间,NULL值的长度为null,占用空间
is null无法判断空值;空值使用"=“或者”<>"来处理(!=)
count()计算时,NULL会忽略,空值会加入计算
一般三种模式:
mysql> select length(null),length(''),length('ad');
+--------------+------------+--------------+
| length(null) | length('') | length('ad') |
+--------------+------------+--------------+
| NULL | 0 | 2 |
+--------------+------------+--------------+
1 row in set (0.00 sec)
mysql> show tables;
+--------------------+
| Tables_in_kgc_ky35 |
+--------------------+
| HP |
| football |
| jinjin |
| kangkang |
| test01 |
| test02 |
| test03 |
| test1 |
| test2 |
| v_HP |
| v_hc |
| v_score |
+--------------------+
12 rows in set (0.00 sec)mysql> select * from HP;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 85.00 | renduo | 3 |
| 2 | cx | 98.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)mysql> alter table HP add length varchar(18);
Query OK, 3 rows affected (0.00 sec)
Records: 3 Duplicates: 0 Warnings: 0mysql> select * from HP;
+------+------+-------+---------+-------+--------+
| id | name | score | address | hobby | length |
+------+------+-------+---------+-------+--------+
| 1 | hz | 90.00 | tianye | 3 | NULL |
| 2 | mdq | 85.00 | renduo | 3 | NULL |
| 2 | cx | 98.00 | guancai | 3 | NULL |
+------+------+-------+---------+-------+--------+
3 rows in set (0.00 sec)
mysql> select * from HP where length is null;
+------+------+-------+---------+-------+--------+
| id | name | score | address | hobby | length |
+------+------+-------+---------+-------+--------+
| 1 | hz | 90.00 | tianye | 3 | NULL |
| 2 | mdq | 85.00 | renduo | 3 | NULL |
| 2 | cx | 98.00 | guancai | 3 | NULL |
+------+------+-------+---------+-------+--------+
3 rows in set (0.00 sec)mysql> select count(length) from HP;
+---------------+
| count(length) |
+---------------+
| 0 |
+---------------+
1 row in set (0.00 sec)
四 连接查询
将来自两个或多个表的记录行结合起来,基于这些表之间的 共同字段,进行数据的查询。
尽量两个表查询,三个表会延缓显示时间
- 内连接
- 左连接
- 右连接
环境准备:
mysql> select * from test02;
+------+------+-------+---------+-------+
| id | name | score | address | hobby |
+------+------+-------+---------+-------+
| 1 | hz | 90.00 | tianye | 3 |
| 2 | mdq | 80.00 | renduo | 3 |
| 2 | cx | 60.00 | guancai | 3 |
+------+------+-------+---------+-------+
3 rows in set (0.00 sec)mysql> select * from kangkang;
+------+--------+------+
| id | name | age |
+------+--------+------+
| 1 | liubei | 56 |
| 2 | lubu | 40 |
| 3 | jiaxu | 75 |
| 4 | cx | 28 |
+------+--------+------+
4 rows in set (0.00 sec)
①内连接
就是两张或多张表中同时符合某种条件的数据记录的组合。通常在 FROM 子句中使用关键字 INNER JOIN 来连接多张表,并使用 ON 子句设置连接条件,内连接是系统默认的表连接,所以在 FROM 子句后可以省略 INNER 关键字,只使用 关键字 JOIN。同时有多个表时,也可以连续使用 INNER JOIN 来实现多表的内连接,
注意:不过为了更好的性能,建议最好不要超过三个表
格式:
select 表1[2].字段1,表1[2].字段2,... from 表1 inner join 表2 on 表1.同名字段=表2.同名字段;
mysql> select test02.id,test02.name from test02 inner join kangkang on test02.name=kangkang.name;
+------+------+
| id | name |
+------+------+
| 2 | cx |
+------+------+
1 row in set (0.00 sec)
内连查询:通过inner join 的方式将两张表指定的相同字段的记录行输出出来
②左连接
在 FROM 子句中使用 LEFT JOIN 或者 LEFT OUTER JOIN 关键字来表示。左连接以左侧表为基础表,接收左表的所有行,并用这些行与右侧参 考表中的记录进行匹配,也就是说匹配左表中的所有行以及右表中符合条件的行
格式:
select * from 表1 left join 表2 on 表1.同名字段=表2.同名字段;
左连接中左表的记录将会全部表示出来,而右表只会显示符合搜索条件的记录,右表记录不足的地方均为 NULL。
mysql> select * from test02 left join kangkang on test02.name=kangkang.name;
+------+------+-------+---------+-------+------+------+------+
| id | name | score | address | hobby | id | name | age |
+------+------+-------+---------+-------+------+------+------+
| 2 | cx | 60.00 | guancai | 3 | 4 | cx | 28 |
| 1 | hz | 90.00 | tianye | 3 | NULL | NULL | NULL |
| 2 | mdq | 80.00 | renduo | 3 | NULL | NULL | NULL |
+------+------+-------+---------+-------+------+------+------+
3 rows in set (0.00 sec)
③右连接
在 FROM 子句中使用 RIGHT JOIN 或者 RIGHT OUTER JOIN 关键字来表示。右连接跟左连接正好相反,它是以右表为基础表,用于接收右表中的所有行,并用这些记录与左表中的行进行匹配
mysql> select * from test02 right join kangkang on test02.name=kangkang.name;
+------+------+-------+---------+-------+------+--------+------+
| id | name | score | address | hobby | id | name | age |
+------+------+-------+---------+-------+------+--------+------+
| 2 | cx | 60.00 | guancai | 3 | 4 | cx | 28 |
| NULL | NULL | NULL | NULL | NULL | 1 | liubei | 56 |
| NULL | NULL | NULL | NULL | NULL | 2 | lubu | 40 |
| NULL | NULL | NULL | NULL | NULL | 3 | jiaxu | 75 |
+------+------+-------+---------+-------+------+--------+------+
4 rows in set (0.00 sec)
在右连接的查询结果集中,除了符合匹配规则的行外,还包括右表中有但是左表中不匹 配的行,这些记录在左表中以 NULL 补足
五 存储过程
前面学习的 MySQL 相关知识都是针对一个表或几个表的单条 SQL 语句,使用这样的SQL 语句虽
然可以完成用户的需求,但在实际的数据库应用中,
有些数据库操作可能会非常复杂,可能会需要多条 SQL 语句一起去处理才能够完成,这时候就可
以使用存储过程, 轻松而高效的去完成这个需求,有点类似shell脚本里的函数
1 存储过程是一组为了完成特定功能的SQL语句集合。 两个点 第一 触发器(定时任务) 第二个判断
2 存储过程这个功能是从5.0版本才开始支持的,它可以加快数据库的处理速度,增强数据库在实际应用中的灵活性。存储过程在使用过程中是将常用或者复杂的工作预先使用SQL语句写好并用一个指定的名称存储起来,这个过程经编译和优化后存储在数据库服务器中。当需要使用该存储过程时,只需要调用它即可。操作数据库的传统 SQL 语句在执行时需要先编译,然后再去执行,跟存储过程一对比,明显存储过程在执行上速度更快,效率更高
1 存储过程的优点:
①执行一次后,会将生成的二进制代码驻留缓冲区,提高执行效率
②SQL语句加上控制语句的集合,灵活性高
③在服务器端存储,客户端调用时,降低网络负载
④可多次重复被调用,可随时修改,不影响客户端调用
⑤可完成所有的数据库操作,也可控制数据库的信息访问权限
语法:
CREATE PROCEDURE <过程名> ( [过程参数[,…] ] ) <过程体>
[过程参数[,…] ] 格式
<过程名>:尽量避免与内置的函数或字段重名
<过程体>:语句
[ IN | OUT | INOUT ] <参数名><类型>
mysql> delimiter $$
#将语句的结束符号从分号;临时改为两个$$(可以自定义)
mysql> create procedure class()
#创建存储过程,过程名为class,不带参数-> begin
#过程体以关键字 BEGIN 开始-> create table class3(id int,name varchar(8),score decimal(5,2));-> insert into class3 values(1,'wsc',98),(2,'ljc',95);-> select * from class3;
#过程体语句-> END $$
#过程体以关键字 END 结束
Query OK, 0 rows affected (0.12 sec)
mysql> DELIMITER ;
#将语句的结束符号恢复为分号
环境准备:
mysql> show tables;
+--------------------+
| Tables_in_kgc_ky35 |
+--------------------+
| HP |
| football |
| kangkang |
| test01 |
| test02 |
| test03 |
| test1 |
| test2 |
| v_HP |
| v_hc |
| v_score |
+--------------------+
11 rows in set (0.00 sec)mysql> select * from kangkang;
+------+--------+------+
| id | name | age |
+------+--------+------+
| 1 | liubei | 56 |
| 2 | lubu | 40 |
| 3 | jiaxu | 75 |
| 4 | cx | 28 |
+------+--------+------+
4 rows in set (0.00 sec)
创建存储
mysql> delimiter $$
mysql> create procedure kangkang ()-> begin-> create table jinjin(id int,name varchar(10),score int(20));-> insert into jinjin values(1,'dieyi',65);-> select * from jinjin;-> END $$
Query OK, 0 rows affected (0.00 sec)
2 调用存储
mysql> call kangkang;
+------+-------+-------+
| id | name | score |
+------+-------+-------+
| 1 | dieyi | 65 |
+------+-------+-------+
1 row in set (0.01 sec)Query OK, 0 rows affected (0.01 sec)
3 查看存储
mysql> show create procedure kangkang\G
*************************** 1. row ***************************Procedure: kangkangsql_mode: PIPES_AS_CONCAT,ANSI_QUOTES,NO_AUTO_VALUE_ON_ZERO,STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTIONCreate Procedure: CREATE DEFINER="root"@"localhost" PROCEDURE "kangkang"()
begin
create table jinjin(id int,name varchar(10),score int(20));
insert into jinjin values(1,'dieyi',65);
select * from jinjin;
END
character_set_client: utf8
collation_connection: utf8_general_ciDatabase Collation: utf8_general_ci
1 row in set (0.00 sec)
mysql> show procedure status like '%kangkang%'\G
*************************** 1. row ***************************Db: kgc_ky35Name: kangkangType: PROCEDUREDefiner: root@localhostModified: 2024-03-27 19:46:16Created: 2024-03-27 19:46:16Security_type: DEFINERComment:
character_set_client: utf8
collation_connection: utf8_general_ciDatabase Collation: utf8_general_ci
1 row in set (0.00 sec)
4 存储过程参数
IN 输入参数:表示调用者向过程传入值(传入值可以是字面量或变量)
OUT 输出参数:表示过程向调用者传出值(可以返回多个值)(传出值只能是变量)
INOUT 输入输出参数:既表示调用者向过程传入值,又表示过程向调用者传出值(值只能是变量)
即表示调用者向过程传入值,又表示过程向调用者传出值(只能是变量)
mysql> delimiter @@
mysql> create procedure yinyin(in inname varchar(40))-> begin-> select * from kangkang where name=inname;-> end @@
Query OK, 0 rows affected (0.01 sec)mysql> call yinyin('cx');
+------+------+------+
| id | name | age |
+------+------+------+
| 4 | cx | 28 |
+------+------+------+
1 row in set (0.00 sec)
5 修改存储
ALTER PROCEDURE <过程名>[<特征>... ]
SECURITY:安全等级
invoker:当定义为INVOKER时,只要执行者有执行权限,就可以成功执行。
6 删除存储
存储过程内容的修改方法是通过删除原有存储过程,之后再以相同的名称创建新的存储过程。
mysql> drop procedure if exists cx;
Query OK, 0 rows affected, 1 warning (0.01 sec)mysql> call cx();
ERROR 1305 (42000): PROCEDURE kgc_ky35.cx does not exist
mysql> show create procedure cx\G;
ERROR 1305 (42000): PROCEDURE cx does not exist
ERROR:
No query specified
相关文章:

高阶SQL语句(二)
一 子查询 也被称作内查询或者嵌套查询,是指在一个查询语句里面还嵌套着另一个查询语 句。子查询语句 是先于主查询语句被执行的,其结果作为外层的条件返回给主查询进行下一 步的查询过滤。 ①子语句可以与主语句所查询的表相同,也可以是不…...

Phoenix伪分布安装
引言 Phoenix是构建在HBase上的一个SQL层,能让我们用标准的JDBC APIs而不是HBase客户端APIs来创建表,插入数据和对HBase数据进行查询。Phoenix完全使用Java编写,作为HBase内嵌的JDBC驱动。Phoenix查询引擎会将SQL查询转换为一个或多个HBase扫…...

Python算法100例-4.6 歌星大奖赛
完整源代码项目地址,关注博主私信源代码后可获取 1.问题描述2.问题分析3.算法设计4.确定程序框架5.完整的程序6.问题拓展7.知识点补充 1.问题描述 在歌星大奖赛中,有10个评委为参赛的选手打分,分数为1~100分。选手最…...

静态路由表学习实验
实验要求:各个pc设备可以通信,并且可以访问外网,假设R1已连接外网 拓扑结构 思路:配置pc机ip地址,子网掩码,和网关(网关地址是上层路由接口的地址),配置路由各个接口地址…...
客户端测试 可测性改进-学习记录
客户端测试面临的挑战 难点: 业务复杂,产品多,技术栈多样 测试过程的痛点: 配置-》执行-〉检查-》结果 手工测试前置配置操作极其繁琐:安装测试包-〉进入debug页面-》设置h-〉设置AB test-》锁定rn包-〉进入业务页…...
机器学习和神经网络9
通过前几次学习,相信对机器学习和神经网络已经有了较为深入的了解。 让我们从一些经典的机器学习算法和实际代码示例开始。: 线性回归:用于预测连续输出的基本算法。你可以从这里找到详细的原理和代码示例。 K-近邻算法 (k-Nearest Neighbors, kNN):一种简单但有效的分类和…...

http模块—http请求练习
题目要求:搭建如下http服务: 1.当浏览器向我们的服务器发送请求时,当请求类型是get请求,请求的url路径地址是/login。响应体结果是登录页面 2.当浏览器向我们的服务器发送请求时,当请求类型是get请求,请求…...

视频号原视频下载使用方法?新人都在用
视频号已经成为我们生活中不可或缺的一种方式,让更多人跃跃欲试,分享自己的生活瞬间或专业知识。然而,有时我们可能需要从视频号中提取原视频,无论是为了备份、编辑还是其他用途。本文将详细解析如何有效、安全地从视频号提取原视…...
用html画一个烟花特效
<!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><title>烟花特效</title><link rel"stylesheet" href"https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.15.2/css/fontawesom…...

SQL-CRUD-1
第一关任务描述 本关任务: 用insert给数据库添加数据 相关知识 有关系student(sno,sname,ssex,sage,sdept),属性对应含义:学号,姓名,性别,所在系。现有的部分元组如下所示 insert 向数据库表插入数据的…...
linux 命令行下的计算器
!!! author 文章目录 1. echo 运算器, 推荐2. bc 计算器, 不推荐3. dc 计算器, 不推荐4. awk计算器. 推荐5. python. 推荐 1. echo 运算器, 推荐 限制是仅能在整数运算时使用 $ echo $((10534)) 70 优点,输入简洁, 支持运算表达式,支持16进制,10进制混合输入. 缺点,不支持浮点…...

Available platform plugins are: linuxfb, minimal, offscreen, vnc.
说明: buildroots根文件中已经移植好了QT的库,但是运行QT交叉编译之后的可执行文件报错: qt.qpa.plugin: Could not find the Qt platform plugin "eglfs" in "" This application failed to start because no Qt platf…...
C++中string容器的修改操作
目录 1.push_back() 尾插字符 2.append() 尾插字符串 3.operator 4.assign 覆盖 5.insert() 指定位置插入 6.erase() 删除 7.replace() 替换 8.swap() 交换 9.pop_back() 尾删 1.push_back() 尾插字符 void push_back (char c) string s("i miss gjj"); s…...

Elasticsearch:虚拟形象辅助和对话驱动的语音到 RAG 搜索
作者:来自 Elastic Sunile Manjee 搜索的演变 搜索已经从产生简单结果的简单文本查询发展成为容纳文本、图像、视频和问题等各种格式的复杂系统。 如今的搜索结果通过生成式人工智能、机器学习和交互式聊天功能得到增强,提供更丰富、更动态且与上下文相…...

测试开发工程师(QA)职业到底需要干些什么?part7:硬件测试工程师QA
概述 硬件测试工程师QA主要负责确保硬件产品在设计、制造和交付过程中的质量和性能。主要任务是进行测试、验证和分析硬件系统、组件和设备,以确保其符合规格和质量标准。下面是硬件测试工程师QA在其工作中常涉及的一些方面: 测试计划和策略:…...

Python基础:标准库 -- pprint (数据美化输出)
1. pprint 库 官方文档 pprint --- 数据美化输出 — Python 3.12.2 文档 pprint — Data pretty printer — Python 3.12.2 documentation 2. 背景 处理JSON文件或复杂的嵌套数据时,使用普通的 print() 函数可能不足以有效地探索数据或调试应用程序。下面通过一…...

Visual Studio 小更新:改善变量的可见性
在 Visual Studio 2022 17.10 预览版 2 中,我们改善了一些小功能,例如:在调试版本中,变量窗口现已可以显示调用堆栈中任意帧的局部变量。 如需体验此功能,请直接安装最新预览版本,就可以知道是怎么一回事儿…...

C++自主点餐系统
一、 题目 设计一个自助点餐系统,方便顾客自己点餐,并提供对餐厅销售情况的统计和管理功能。 二、 业务流程图 三、 系统功能结构图 四、 类的设计 五、 程序代码与说明 头文件1. SystemMap.h #pragma once #ifndef SYSTEMMAP #define SYSTEMMAP #in…...

jconsole jvisualvm
jconsole 打开方式 命令行输入 jconsole双击想要连接的应用 界面展示 jvisualvm 打开方式 命令行输入 jvisualvm双击想要连接的应用 可以安装插件,比如 Visual GC 直观看到 GC 过程...
python vtkUnstructuredGrid 转 vtkAlgorithmOutput_
在VTK (Vtk.py)中,vtkUnstructuredGrid对象可以通过多种方式转换为vtkAlgorithmOutput_对象。这种转换通常在管道中使用,以将一个算法的输出传递给另一个算法作为其输入。 以下是一个简单的例子,展示如何将vtkUnstructuredGrid对象转换为 v…...
模型参数、模型存储精度、参数与显存
模型参数量衡量单位 M:百万(Million) B:十亿(Billion) 1 B 1000 M 1B 1000M 1B1000M 参数存储精度 模型参数是固定的,但是一个参数所表示多少字节不一定,需要看这个参数以什么…...
Oracle查询表空间大小
1 查询数据库中所有的表空间以及表空间所占空间的大小 SELECTtablespace_name,sum( bytes ) / 1024 / 1024 FROMdba_data_files GROUP BYtablespace_name; 2 Oracle查询表空间大小及每个表所占空间的大小 SELECTtablespace_name,file_id,file_name,round( bytes / ( 1024 …...

云启出海,智联未来|阿里云网络「企业出海」系列客户沙龙上海站圆满落地
借阿里云中企出海大会的东风,以**「云启出海,智联未来|打造安全可靠的出海云网络引擎」为主题的阿里云企业出海客户沙龙云网络&安全专场于5.28日下午在上海顺利举办,现场吸引了来自携程、小红书、米哈游、哔哩哔哩、波克城市、…...

【Java_EE】Spring MVC
目录 Spring Web MVC 编辑注解 RestController RequestMapping RequestParam RequestParam RequestBody PathVariable RequestPart 参数传递 注意事项 编辑参数重命名 RequestParam 编辑编辑传递集合 RequestParam 传递JSON数据 编辑RequestBody …...

Mysql中select查询语句的执行过程
目录 1、介绍 1.1、组件介绍 1.2、Sql执行顺序 2、执行流程 2.1. 连接与认证 2.2. 查询缓存 2.3. 语法解析(Parser) 2.4、执行sql 1. 预处理(Preprocessor) 2. 查询优化器(Optimizer) 3. 执行器…...

七、数据库的完整性
七、数据库的完整性 主要内容 7.1 数据库的完整性概述 7.2 实体完整性 7.3 参照完整性 7.4 用户定义的完整性 7.5 触发器 7.6 SQL Server中数据库完整性的实现 7.7 小结 7.1 数据库的完整性概述 数据库完整性的含义 正确性 指数据的合法性 有效性 指数据是否属于所定…...

论文阅读笔记——Muffin: Testing Deep Learning Libraries via Neural Architecture Fuzzing
Muffin 论文 现有方法 CRADLE 和 LEMON,依赖模型推理阶段输出进行差分测试,但在训练阶段是不可行的,因为训练阶段直到最后才有固定输出,中间过程是不断变化的。API 库覆盖低,因为各个 API 都是在各种具体场景下使用。…...
机器学习的数学基础:线性模型
线性模型 线性模型的基本形式为: f ( x ) ω T x b f\left(\boldsymbol{x}\right)\boldsymbol{\omega}^\text{T}\boldsymbol{x}b f(x)ωTxb 回归问题 利用最小二乘法,得到 ω \boldsymbol{\omega} ω和 b b b的参数估计$ \boldsymbol{\hat{\omega}}…...

MySQL体系架构解析(三):MySQL目录与启动配置全解析
MySQL中的目录和文件 bin目录 在 MySQL 的安装目录下有一个特别重要的 bin 目录,这个目录下存放着许多可执行文件。与其他系统的可执行文件类似,这些可执行文件都是与服务器和客户端程序相关的。 启动MySQL服务器程序 在 UNIX 系统中,用…...
Qt Quick Controls模块功能及架构
Qt Quick Controls是Qt Quick的一个附加模块,提供了一套用于构建完整用户界面的UI控件。在Qt 6.0中,这个模块经历了重大重构和改进。 一、主要功能和特点 1. 架构重构 完全重写了底层架构,与Qt Quick更紧密集成 移除了对Qt Widgets的依赖&…...