多表更新

假定我们有两张表,一张表为Product表存放产品信息,其中有产品价格列Price;另外一张表是ProductPrice表,我们要将ProductPrice表中的价格字段Price更新为Price表中价格字段的80%。

在Mysql中我们有几种手段可以做到这一点,一种是update table1 t1, table2 ts ...的方式:

UPDATE product p, productPrice pp 
SET pp.price = pp.price * 0.8 
WHERE p.productId = pp.productId 
AND p.dateCreated < '2004-01-01'

另外一种方法是使用inner join然后更新:

代码如下:

UPDATE product p 
INNER JOIN productPrice pp 
ON p.productId = pp.productId 
SET pp.price = pp.price * 0.8 
WHERE p.dateCreated < '2004-01-01' 

另外我们也可以使用left outer join来做多表update,比方说如果ProductPrice表中没有产品价格记录的话,将Product表的isDeleted字段置为1,如下sql语句:

代码如下:

UPDATE product p 
LEFT JOIN productPrice pp 
ON p.productId = pp.productId 
SET p.deleted = 1 
WHERE pp.productId IS null 

另外,上面的几个例子都是两张表之间做关联,但是只更新一张表中的记录,其实是可以同时更新两张表的,如下sql:

代码如下:

UPDATE product p 
INNER JOIN productPrice pp 
ON p.productId = pp.productId 
SET pp.price = pp.price * 0.8, 
p.dateUpdate = CURDATE() 
WHERE p.dateCreated < '2004-01-01' 

两张表做关联,更新了ProductPrice表的price字段和Product表字段的dateUpdate两个字段。

---------------------------------------------------------------------------------华丽分割线---------------------------------------------------------------------------------

多表查询

新建两张表:

表1:student      表2:course

        

(此时这样建表只是为了演示连接SQL语句,当然实际开发中我们不会这样建表,实际开发中这两个表会有自己不同的主键。)

一、外连接

外连接可分为:左连接、右连接、完全外连接。

1、左连接  left join 或 left outer join

SQL语句:select * from student left join course on student.ID=course.ID

执行结果:左外连接包含left join左表所有行,如果左表中某行在右表没有匹配,则结果中对应行右表的部分全部为空(NULL).

注:此时我们不能说结果的行数等于左表数据的行数。当然此处查询结果的行数等于左表数据的行数,因为左右两表此时为一对一关系。

2、右连接  right join 或 right outer join

SQL语句:select * from student right join course on student.ID=course.ID

执行结果:右外连接包含right join右表所有行,如果左表中某行在右表没有匹配,则结果中对应左表的部分全部为空(NULL)。

注:同样此时我们不能说结果的行数等于右表的行数。当然此处查询结果的行数等于左表数据的行数,因为左右两表此时为一对一关系。

3、完全外连接  full join 或 full outer join

SQL语句:select * from student full join course on student.ID=course.ID

执行结果:完全外连接包含full join左右两表中所有的行,如果右表中某行在左表中没有匹配,则结果中对应行右表的部分全部为空(NULL),如果左表中某行在右表中没有匹配,则结果中对应行左表的部分全部为空(NULL)。

二、内连接  join 或 inner join

SQL语句:select * from student inner join course on student.ID=course.ID

执行结果:inner join 是比较运算符,只返回符合条件的行。此时相当于:select * from student,course where student.ID=course.ID

三、交叉连接 cross join

1.概念:没有 WHERE 子句的交叉联接将产生连接所涉及的表的笛卡尔积。第一个表的行数乘以第二个表的行数等于笛卡尔积结果集的大小。

SQL语句:select * from student cross join course

执行结果:如果我们在此时给这条SQL加上WHERE子句的时候比如SQL:select * from student cross join course where student.ID=course.ID

此时将返回符合条件的结果集,结果和inner join所示执行结果一样。

四、两表关系为一对多,多对一或多对多时的连接语句

当然上面两表为一对一关系,那么如果表A和表B为一对多、多对一或多对多的时候,我们又该如何写连接SQL语句呢?

其实两表一对多的SQL语句和一对一的SQL语句的写法都差不多,只是查询的结果不一样,当然两表也要略有改动。

比如表1的列可以改为:

Sno Name Cno

表2的列可以改为:

Cno CName

这样两表就可以写一对多和多对一的SQL语句了,写法和上面的一对一SQL语句一样。

下面介绍一下当两表为多对多的时候我们该如何建表以及些SQL语句。

新建三表:

表A:  student 截图如下:     表B:  course 截图如下:   表C:  student_course 截图如下:

                      

一个学生可以选择多门课程,一门课程可以被多个学生选择,因此学生表student和课程表course之间是多对多的关系。

当两表为多对多关系的时候,我们需要建立一个中间表student_course,中间表至少要有两表的主键,当然还可以有别的内容。

SQL语句:select s.Name,C.Cname from student_course as sc left join student as s on s.Sno=sc.Sno left join course as c on c.Cno=sc.Cno

执行结果:此条SQL执行的结果是学生选课的情况。

---------------------------------------------------------------------------------华丽分割线---------------------------------------------------------------------------------

distinct的特殊用法:select  count(*) from (select distinct cdkey from tbl_alipay) s;

distinct的另一种方法:

select *, count(distinct name) from table group by name

结果:

id name count(distinct name)
   1 a 1
   2 b 1
   3 c 1

最后一项是多余的,不用管就行了,目的达到

group by 必须放在 order by 和 limit之前,不然会报错

引用自:http://www.jb51.net/article/24717.htm

SQL的多表操作的更多相关文章

  1. SQL语句之表操作

    SQL语句系列 1.SQL语句之行操作 2.SQL语句之表操作 3.SQL语句之数据库操作 4.SQL语句之用户管理 写在前面 在上一篇博文里面我整理了“行”级别的操作,分别是“增(insert).删 ...

  2. sql总结-----数据表操作

    数据表概述 表示一种最常见的组织数据的方式,一张表一般有多个列(即多个字段). oracle提供了多种内置的列的数据类型,常用的有以下五种: 1.字符类型 字符数据类型用于声明包含字母.数字数据的字段 ...

  3. 一头扎进sql之多表操作

    一.多表查询时NULL值处理 要求返回比"allen"工资低的所有员工 select  a.ename,a.conn from emp a  where  a.conn  < ...

  4. SQL语句总结---表操作

    https://blog.csdn.net/hallomrzhang/article/details/85010014 表的操作 1.查看表结构 desc 表名 2.创建表结构的语法 create t ...

  5. SQL语句之数据库操作

    SQL语句系列 1.SQL语句之行操作 2.SQL语句之表操作 3.SQL语句之数据库操作 4.SQL语句之用户管理 占坑,带写……

  6. SQL语句之行操作

    SQL语句系列 1.SQL语句之行操作 2.SQL语句之表操作 3.SQL语句之数据库操作 4.SQL语句之用户管理 关系型数据库的存储形式 在关系型数据库中,数据都是以类似于Excel表格的形式存储 ...

  7. Sql Server系列:数据表操作

    表是用来存储数据和操作数据的逻辑结构,用来组织和存储数据,关系数据库中的所有数据都表现为表的形式,数据表由行和列组成.SQL Server中的数据表分为临时表和永久表,临时表存储在tempdb系统数据 ...

  8. SQL server基础知识(表操作、数据约束、多表链接查询)

    SQL server基础知识 一.基础知识 (1).存储结构:数据库->表->数据 (2).管理数据库 增加:create database 数据库名称 删除:drop database ...

  9. SQL Server 基础 01 数据库、表操作

    对着书慢慢学习,一天一点点! 数据库操作 (create.alter.drop)  --3-3-1 /create database 语句创建数据库 create database testSQL - ...

随机推荐

  1. C#_delegate - 异步调用实例 BeginInvoke EndInvoke event

    using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.T ...

  2. Eclipse 各种包说明

    2001年11月7日 ,Eclipse 1.0发布 半年之后,2002年6月27日Eclipse进入了2.0时代.2.0时代的Eclipse经历了2.0和2.1两个大的版本.其中2.0在 之后又推出了 ...

  3. SQL SERVER 2005 同步复制

    what SQL SERVER2005复制是在不同数据库间保持数据结构和数据内容同步更新的一种方案. 由三部分构成: 发布服务器:包含了需要被发布的数据库,也就是需要向其它数据源分发内容的源数据库. ...

  4. View绘制详解(二),从setContentView谈起

    掐指一算,本来今天该介绍View的测量了,可是要说View的测量,那就要从setContentView谈起了,setContentView本身涉及到的东西也是挺多的,所以今天我们就先来看看这个setC ...

  5. jsp HTTP Status 405 - HTTP method GET is not supported by this URL

    package myservlet.control; import java.io.IOException; import java.io.PrintWriter; import javax.serv ...

  6. Apache配置虚拟主机后,不能访问localhost的问题

    今天想试用一下php7,但是发现php7只支持Apache2.4版本,而我电脑上的Apache是2.2版本,为了想尝鲜,就必须去下载新的Apache2.4 php7和apache2.4安装整合以后,l ...

  7. MySQL创建/删除/清空表,添加/删除字段

    创建表: create table tablename (column_name column_type); create table table_name( id int not null auto ...

  8. 网站压力测试工具webbench 安装与使用

    webbench最多可以模拟3万个并发连接去测试网站的负载能力,个人感觉要比Apache自带的ab压力测试工具好用,安装使用也特别方便,并且非常小. 主要是 -t 参数用着比较爽,下面参考了张宴的文章 ...

  9. oracle学习总结5(游标、触发器、过程、方法)

    1:捕获plsql抛出的异常 declarev_ename emp.ename%type;beginselect ename into v_ename from emp where empno=10; ...

  10. git命令(流程)

    1,配置你的信息: git config --global user.name 你的名字 git config --global user.email 你的邮箱 --global 表示所有git仓库都 ...