python 之 数据库(多表查询之连接查询、子查询、pymysql模块的使用)
10.10 多表连接查询
10.101 内连接
把两张表有对应关系的记录连接成一张虚拟表
- select * from emp,dep; #连接两张表的笛卡尔积
- select * from emp,dep where emp.dep_id = dep.id; # 不推荐用where连接表
- select * from emp inner join dep on emp.dep_id = dep.id; #推荐
- +----+-----------+--------+------+--------+------+--------------+
- | id | name | sex | age | dep_id | id | name |
- +----+-----------+--------+------+--------+------+--------------+
- | 1 | egon | male | 18 | 200 | 200 | 技术 |
- | 2 | alex | female | 48 | 201 | 201 | 人力资源 |
- | 3 | wupeiqi | male | 38 | 201 | 201 | 人力资源 |
- | 4 | yuanhao | female | 28 | 202 | 202 | 销售 |
- | 5 | liwenzhou | male | 18 | 200 | 200 | 技术 |
- +----+-----------+--------+------+--------+------+--------------+
- #应用:
- select * from emp,dep where emp.dep_id = dep.id and dep.name = "技术";
- select * from emp inner join dep on emp.dep_id = dep.id where dep.name = "技术";
- +----+-----------+------+------+--------+------+--------+
- | id | name | sex | age | dep_id | id | name |
- +----+-----------+------+------+--------+------+--------+
- | 1 | egon | male | 18 | 200 | 200 | 技术 |
- | 5 | liwenzhou | male | 18 | 200 | 200 | 技术 |
- +----+-----------+------+------+--------+------+--------+
应用
10.102 左连接
在内连接的基础上,保留左边没有对应关系的记录
- select * from emp left join dep on emp.dep_id = dep.id;
- +----+------------+--------+------+--------+------+--------------+
- | id | name | sex | age | dep_id | id | name |
- +----+------------+--------+------+--------+------+--------------+
- | 1 | egon | male | 18 | 200 | 200 | 技术 |
- | 5 | liwenzhou | male | 18 | 200 | 200 | 技术 |
- | 2 | alex | female | 48 | 201 | 201 | 人力资源 |
- | 3 | wupeiqi | male | 38 | 201 | 201 | 人力资源 |
- | 4 | yuanhao | female | 28 | 202 | 202 | 销售 |
- | 6 | jingliyang | female | 18 | 204 | NULL | NULL |
- +----+------------+--------+------+--------+------+--------------+
10.103 右连接
在内连接的基础上,保留右边没有对应关系的记录
- select * from emp right join dep on emp.dep_id = dep.id;
- +------+-----------+--------+------+--------+------+--------------+
- | id | name | sex | age | dep_id | id | name |
- +------+-----------+--------+------+--------+------+--------------+
- | 1 | egon | male | 18 | 200 | 200 | 技术 |
- | 2 | alex | female | 48 | 201 | 201 | 人力资源 |
- | 3 | wupeiqi | male | 38 | 201 | 201 | 人力资源 |
- | 4 | yuanhao | female | 28 | 202 | 202 | 销售 |
- | 5 | liwenzhou | male | 18 | 200 | 200 | 技术 |
- | NULL | NULL | NULL | NULL | NULL | 203 | 运营 |
- +------+-----------+--------+------+--------+------+--------------+
10.104 全连接
在内连接的基础上,保留左、右边没有对应关系的记录,并去重
- select * from emp left join dep on emp.dep_id = dep.id
- union
- select * from emp right join dep on emp.dep_id = dep.id;
- +------+------------+--------+------+--------+------+--------------+
- | id | name | sex | age | dep_id | id | name |
- +------+------------+--------+------+--------+------+--------------+
- | 1 | egon | male | 18 | 200 | 200 | 技术 |
- | 5 | liwenzhou | male | 18 | 200 | 200 | 技术 |
- | 2 | alex | female | 48 | 201 | 201 | 人力资源 |
- | 3 | wupeiqi | male | 38 | 201 | 201 | 人力资源 |
- | 4 | yuanhao | female | 28 | 202 | 202 | 销售 |
- | 6 | jingliyang | female | 18 | 204 | NULL | NULL |
- | NULL | NULL | NULL | NULL | NULL | 203 | 运营 |
- +------+------------+--------+------+--------+------+--------------+
补充:多表连接可以不断地与虚拟表连接
- #查找各部门最高工资
- select t1.* from emp as t1 inner join (select post,max(salary) as ms from emp group by post) as t2
- on t1.post = t2.post
- where t1.salary = t2.ms;
10.11 子查询
把一个查询语句用括号括起来,当做另外一条查询语句的条件去用,称为子查询
- #查询技术部员工的名字
- select emp.name from emp inner join dep on emp.dep_id = dep.id where dep.name="技术";#连接查询
- select name from emp where dep_id =(select id from dep where name="技术"); #子查询
- +-----------+
- | name |
- +-----------+
- | egon |
- | liwenzhou |
- +-----------+
- #查询平均年龄在25岁以上的部门名 #子查询
- select name from dep where id in (select dep_id from emp group by dep_id having avg(age) > 25);
- select dep.name from emp inner join dep on emp.dep_id = dep.id #连接查询
- group by dep.name
- having avg(age) > 25;
- +--------------+
- | name |
- +--------------+
- | 人力资源 |
- | 销售 |
- +--------------+
- #查询每个部门最新入职的那位员工
- select t1.id,t1.name,t1.post,t1.hire_date,t2.post,t2.max_date from (emp as t1) inner join
- (select post,max(hire_date) as max_date from emp group by post) as t2 #拿到最大雇佣时间
- on t1.post = t2.post
- where t1.hire_date = t2.max_date;
- +----+--------+-----------------------------------------+----
- | id | name | post | hire_date | post | max_date |
- +----+--------+-----------------------------------------+-----
- | 1 | egon | 外交大使 | 2017-03-01 | 外交大使 | 2017-03-01 |
- | 2 | alex | teacher | 2015-03-02 | teacher | 2015-03-02 |
- | 13 | 格格 | sale | 2017-01-27 | sale | 2017-01-27 |
- | 14 | 张野 | operation| 2016-03-11 | operation| 2016-03-11 |
- +----+--------+-----------------------------------------+-----
exists( ):括号内的值存在时满足条件
- select * from emp where exists (select id from dep where id > 3); #找到所有
10.12 pymysql模块的使用
10.121 pymysql查
- import pymysql #pip3 install pymysql
- conn=pymysql.connect( #连接
- host='127.0.0.1',
- port=3306,
- user='root',
- password='',
- database='db2',
- charset='utf8')
- cursor=conn.cursor(pymysql.cursors.DictCursor)#以字典形式显示表的记录
- rows=cursor.execute('show tables;') #1 显示受影响的行数(row),此处为有表的条数
- print(rows)
- rows=cursor.execute('select * from emp;') #18 此处rows为emp表内有记录的条数
- print(rows)
-
- print(cursor.fetchone()) #查看一条记录 一个字典{key:value}
- print(cursor.fetchmany(2)) #查看多条记录 [{key:value},]
- #print(cursor.fetchall()) #查看所有记录 强调:下一次查找是接着上一次查找的位置继续
-
- cursor.scroll(0,'absolute') #绝对移动,以0位置为参照显示
- print(cursor.fetchone())
-
- cursor.scroll(1,'relative') #相对移动,相对当前位置移动1条记录
- print(cursor.fetchone())
-
- cursor.close()#光标
- conn.close()
10.122 防止sql注入问题
在服务端防止sql注入问题:不要自己拼接字符串,让pymysql模块去拼接,pymysql拼接时会过滤非法字符
- import pymysql
- conn=pymysql.connect(
- host='127.0.0.1',
- port=3306,
- user='root',
- password='',
- database='db2',
- charset='utf8'
- )
- cursor=conn.cursor(pymysql.cursors.DictCursor)
-
- inp_user=input('用户名>>:').strip() #inp_user=""
- inp_pwd=input('密码>>:').strip() #inp_pwd=""
- sql="select * from user where username=%s and password=%s"
- print(sql)
- rows=cursor.execute(sql,(inp_user,inp_pwd))#输入的用户名和密码中的非法字符会被过滤掉
- if rows:
- print('登录成功')
- else:
- print('登录失败')
- cursor.close()
- conn.close()
10.123 pymysql增删改
- import pymysql
- conn=pymysql.connect(
- host='127.0.0.1',
- port=3306,
- user='root',
- password='',
- database='db2',
- charset='utf8')
- cursor=conn.cursor(pymysql.cursors.DictCursor)
- sql='insert into user(username,password) values(%s,%s)' #插入单行记录
- rows=cursor.execute(sql,('EGON',''))
- print(rows)
- print(cursor.lastrowid) #显示当前最后一行的id
-
- sql='insert into user(username,password) values(%s,%s)' #一次插入多行记录
- rows=cursor.executemany(sql,[('lwz','123'),('evia','455'),('lsd','333')])
- print(rows)
-
- rows=cursor.execute('update user set username="alexSB" where id=2')#修改记录
- print(rows)
-
- conn.commit() # 只有commit提交才会完成真正的修改
- cursor.close()
- conn.close()
python 之 数据库(多表查询之连接查询、子查询、pymysql模块的使用)的更多相关文章
- MySQL数据库学习笔记(六)----MySQL多表查询之外键、表连接、子查询、索引
本章主要内容: 一.外键 二.表连接 三.子查询 四.索引 一.外键: 1.什么是外键 2.外键语法 3.外键的条件 4.添加外键 5.删除外键 1.什么是外键: 主键:是唯一标识一条记录,不能有重复 ...
- MySQL数据库学习笔记----MySQL多表查询之外键、表连接、子查询、索引
本章主要内容: 一.外键 二.表连接 三.子查询 四.索引 一.外键: 1.什么是外键 2.外键语法 3.外键的条件 4.添加外键 5.删除外键 1.什么是外键: 主键:是唯一标识一条记录,不能有重复 ...
- MS sql server 基础知识回顾(二)-表连接和子查询
五.表连接 当数据表中存在许多重复的冗余信息时,就要考虑将这些信息建在另一张新表中,在新表中为原表设置好外键,在进行数据查询的时候,就要使用到连接了,表连接就好像两根线,线的两端分别连接两张表的不同字 ...
- MySQL多表查询之外键、表连接、子查询、索引
MySQL多表查询之外键.表连接.子查询.索引 一.外键: 1.什么是外键 2.外键语法 3.外键的条件 4.添加外键 5.删除外键 1.什么是外键: 主键:是唯一标识一条记录,不能有重复的,不允许为 ...
- mysql学习笔记-- 多表查询之外键、表连接、子查询、索引
本章主要内容: 一.外键 二.表连接 三.子查询 四.索引 一.外键: 1.什么是外键 2.外键语法 3.外键的条件 4.添加外键 5.删除外键 1.什么是外键: 主键:是唯一标识一条记录,不能有重复 ...
- 数据库——SQL-SERVER练习(1)连接与子查询
一.实验准备 1.复制实验要求文件及“CREATE-TABLES.SQL”文件, 粘贴到本地机桌面. 2.启动SQL-SERVER服务. 3. 运行查询分析器, 点击菜单<文件>/< ...
- mysql表查询、多表查询(增强查询的使用)子查询、合并查询,外连接,mysql5种约束,自增长
一.查询加强 1.在mysql中,日期类型可以直接比较,需要注意格式 2.%:表示0到多个字符, _:表示单个字符 exp:显示第二个字符为大写O的所有员工的姓名和工资 select name fr ...
- ylb:SQL 表的高级查询-多表连接和子查询
ylbtech-SQL Server: SQL Server-表的高级查询-多表连接和子查询 SQL Server 表的高级查询-多表连接和子查询. 1,ylb:表的高级查询-多表连接和子查询 返回顶 ...
- oracle之复杂查询(下):子查询
复杂查询(下):子查询 8. 1 非关联子查询:返回的值可以被外部查询使用.子查询可以独立执行的(且仅执行一次). 8.1.1 单行单列子查询,子查询仅返回一个值,也称为标量子查询,采用单行比较运算符 ...
- mysql加强(6)~子查询简单介绍、子查询分类
一.子查询简单介绍 1.什么是子查询? 一个查询之中嵌套了其他的若干查询. 在使用select 语句查询时,有时候where的查询条件中的限制条件不是一个确定的值,而是一个来自于另一个查询的结果. 子 ...
随机推荐
- vue+element 表格formatter数据格式化并且插入html标签
前言 vue中 element框架,其中表格组件,我既要行内数据格式化,又要插入html标签 一贯思维,二者不可兼得也 一.element 表格 数据格式化 demo <el-table-col ...
- 修改docker默认存储路径
默认情况下,docker镜像的默认存储路径是/var/lib/docker,这相当于直接挂载系统目录下,而一般在搭系统时,这个区都不会太大,所以如果长期使用docker开发应用,就需要把默认的路径更改 ...
- receipt
receipt - 必应词典 美[riˈsiːt]英[rɪ'siːt] n.收据:收入:接受:字据 v.开收据 网络收到:收条:发票 变形复数:receipts: 搭配give receipt:sig ...
- Oracle中的统计信息
一.什么是统计信息 统计信息主要是描述数据库中表,索引的大小,规模,数据分布状况等的一类信息.例如,表的行数,块数,平均每行的大小,索引的leaf blocks,索引字段的行数,不同值的大小等,都属于 ...
- Python脚本基础运算和算法
原文地址:https://www.cnblogs.com/ailiailan/p/10141741.html 通过关注“常见”脚本,是对代码的一个很好的学习和总结的方式. 1.冒泡排序 lis = [ ...
- Java对象为啥要实现Serializable接口
Serializable接口概述 Serializable是java.io包中定义的.用于实现Java类的序列化操作而提供的一个语义级别的接口.Serializable序列化接口没有任何方法或者字段, ...
- Tosca :配置环境参数
# 跟Modules TestCases并列 ,右键创建 #再右键创建配置(结构自己安排) #再创建配置参数 #使用配置参数 #引用配置的环境参数
- pip install失败报错解决方案
cmd pip install 某些包时报错 pip install Consider using the `--user` option or check the permissions. 只需要p ...
- 主外键 设置 on update cascade 和on delete cascade 的区别
on update cascade 和on delete cascade 的区别 这是数据库外键定义的一个可选项,用来设置当主键表中的被参考列的数据发生变化时,外键表中响应字段的变换规则的.updat ...
- colock
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android=&quo ...