数据库test
dept +--------+------------+----------+ | deptno | dname | loc | +--------+------------+----------+ | 10 | ACCOUNTING | NEW YORK | | 20 | RESEARCH | DALLAS | | 30 | SALES | CHICAGO | | 40 | OPERATIONS | BOSTON | +--------+------------+----------+ emp +-------+----------+-----------+------+------------+---------+---------+--------+ | empno | ename | job | mgr | hiredate | sal | comm | deptno | +-------+----------+-----------+------+------------+---------+---------+--------+ | 7369 | SMITH | CLERK | 7902 | 1980-12-17 | 5000.00 | NULL | 20 | | 7499 | ALLEN | SALESMAN | 7698 | 1981-02-20 | 1600.00 | 300.00 | 30 | | 7521 | WARD | SALESMAN | 7698 | 1981-02-22 | 1250.00 | 500.00 | 30 | | 7566 | JONES | MANAGER | 7839 | 1981-04-02 | 2975.00 | NULL | 20 | | 7654 | MARTIN | SALESMAN | 7698 | 1981-09-28 | 1250.00 | 1400.00 | 30 | | 7698 | BLAKE | MANAGER | 7839 | 1981-05-01 | 2850.00 | NULL | 30 | | 7782 | CLARK | MANAGER | 7839 | 1981-06-09 | 2450.00 | NULL | 10 | | 7788 | SCOTT | ANALYST | 7566 | 1987-07-13 | 3000.00 | NULL | 20 | | 7839 | KING | PRESIDENT | NULL | 1981-11-17 | 5000.00 | NULL | 10 | | 7844 | TURNER | SALESMAN | 7698 | 1981-09-08 | 1500.00 | 0.00 | 30 | | 7876 | ADAMS | CLERK | 7788 | 1987-07-13 | 1100.00 | NULL | 20 | | 7900 | JAMES | CLERK | 7698 | 1981-12-03 | 950.00 | NULL | 30 | | 7902 | FORD | ANALYST | 7566 | 1981-12-03 | 3000.00 | NULL | 20 | | 7934 | MILLER | CLERK | 7782 | 1982-01-23 | 1300.00 | NULL | 10 | | 8000 | zhangsan | CLERK | 7782 | 1982-01-23 | 1300.00 | NULL | 50 | +-------+----------+-----------+------+------------+---------+---------+--------+
子查询(sub query)
概念:就是把一个查询的结果当作另一个查询的条件或者一张新表,进行查询或者连接。可以多个查询嵌套。
(1)求最高工资的员工信息(把一个查询的结果当作另一个查询的条件)
分步骤做:
1.先求出员工中的最高工资5000
2.把最高工资5000当作条件,查出工资为5000的员工信息
select max(sal) from emp e; +----------+ | max(sal) | +----------+ | 5000.00 | +----------+ select * from emp where sal = 5000; +-------+-------+-----------+------+------------+---------+------+--------+ | empno | ename | job | mgr | hiredate | sal | comm | deptno | +-------+-------+-----------+------+------------+---------+------+--------+ | 7369 | SMITH | CLERK | 7902 | 1980-12-17 | 5000.00 | NULL | 20 | | 7839 | KING | PRESIDENT | NULL | 1981-11-17 | 5000.00 | NULL | 10 | +-------+-------+-----------+------+------------+---------+------+--------+
子查询做:
select * from emp where sal = (select max(sal) from emp); +-------+-------+-----------+------+------------+---------+------+--------+ | empno | ename | job | mgr | hiredate | sal | comm | deptno | +-------+-------+-----------+------+------------+---------+------+--------+ | 7369 | SMITH | CLERK | 7902 | 1980-12-17 | 5000.00 | NULL | 20 | | 7839 | KING | PRESIDENT | NULL | 1981-11-17 | 5000.00 | NULL | 10 | +-------+-------+-----------+------+------------+---------+------+--------+
(2)每个部门的最高工资的员工(把一个查询的结果当作一张新表)
分步骤做:
1.先求出每个部门最高工资以及其部门编号,把结果当作一个新表a
(select max(sal) msal, deptno from emp group by deptno) a
2.把新表a与emp表连接,再选择出员工信息。
select * from emp b inner join a on b.deptno=a.deptno and b.sal = a.msal;
子查询做:
select * from emp b inner join -> (select max(sal) msal, deptno from emp group by deptno) a -> on b.deptno=a.deptno and b.sal = a.msal; +-------+----------+-----------+------+------------+---------+------+--------+---------+--------+ | empno | ename | job | mgr | hiredate | sal | comm | deptno | msal | deptno | +-------+----------+-----------+------+------------+---------+------+--------+---------+--------+ | 7369 | SMITH | CLERK | 7902 | 1980-12-17 | 5000.00 | NULL | 20 | 5000.00 | 20 | | 7698 | BLAKE | MANAGER | 7839 | 1981-05-01 | 2850.00 | NULL | 30 | 2850.00 | 30 | | 7839 | KING | PRESIDENT | NULL | 1981-11-17 | 5000.00 | NULL | 10 | 5000.00 | 10 | | 8000 | zhangsan | CLERK | 7782 | 1982-01-23 | 1300.00 | NULL | 50 | 1300.00 | 50 | +-------+----------+-----------+------+------------+---------+------+--------+---------+--------+
case when语句
概念:可以配合select工作, 把一列的取值根据不同的条件进行翻译类似于 java 中的if else if。
语句格式:
case
when 条件1 then 结果1
when 条件2 then 结果2
...
else 结果n
end举例:把emp表中的员工工资输出,2000以下显示低工资,2000~3000显示中等,3000以上显示高工资
mysql> select empno, ename, sal, -> case -> when sal <= 2000 then '低工资' -> when sal >2000 and sal <=3000 then '中等工资' -> else '高工资' -> end 工资级别 from emp; +-------+----------+---------+----------+ | empno | ename | sal | 工资级别 | +-------+----------+---------+----------+ | 7369 | SMITH | 5000.00 | 高工资 | | 7499 | ALLEN | 1600.00 | 低工资 | | 7521 | WARD | 1250.00 | 低工资 | | 7566 | JONES | 2975.00 | 中等工资 | | 7654 | MARTIN | 1250.00 | 低工资 | | 7698 | BLAKE | 2850.00 | 中等工资 | | 7782 | CLARK | 2450.00 | 中等工资 | | 7788 | SCOTT | 3000.00 | 中等工资 | | 7839 | KING | 5000.00 | 高工资 | | 7844 | TURNER | 1500.00 | 低工资 | | 7876 | ADAMS | 1100.00 | 低工资 | | 7900 | JAMES | 950.00 | 低工资 | | 7902 | FORD | 3000.00 | 中等工资 | | 7934 | MILLER | 1300.00 | 低工资 | | 8000 | zhangsan | 1300.00 | 低工资 | +-------+----------+---------+----------+
注意:工资级别不加引号,else可有可无。
授权管理:
有两个关键字:grant 授权 revoke 回收权限
注意:普通用户只能授权自己创建的数据库数据权限,管理员用户(root)可以授权所有数据库权限。
创建一个新用户: create user ‘用户名’ identified by ‘用户密码’
create user 'wang' identified by 'wang';
登陆之后新用户没有权限访问test库 在root用户下:
用 grant 权限 on 数据库 to 用户名 给新用户某给数据库的某个权限
grant select on test.* to wang
用 revoke权限 on 数据库 from 用户名 收回某给用户的某个权限
revoke select on test.* from wang;
权限比如:select(选择权限) update(修改权限).....
事物(transaction)
概念:把一组sql语句当作一个整体,这些sql语句要么全部执行完,要么一个也不执行,执行中过程有一个sql语句失败了,以前的sql语句也要撤销。相当于原子操作。
在MySQL中的事物控制默认是一条语句为一个事物。要让一组sql语句为事物,用关键字begin commit rollback`来控制事务
begin(表示事物开始) commit (表示提交sql语句为事物) rollback(表示撤回以上的sql语句)mysql> begin; Query OK, 0 rows affected (0.00 sec) mysql> update emp set sal=8888 where empno=7369; Query OK, 0 rows affected (0.00 sec) Rows matched: 0 Changed: 0 Warnings: 0 mysql> commit; Query OK, 0 rows affected (0.00 sec) mysql> select * from emp; +-------+----------+-----------+------+------------+---------+---------+--------+ | empno | ename | job | mgr | hiredate | sal | comm | deptno | +-------+----------+-----------+------+------------+---------+---------+--------+ | 7369 | SMITH | CLERK | 7902 | 1980-12-17 | 8888.00 | NULL | 20 | | 7499 | ALLEN | SALESMAN | 7698 | 1981-02-20 | 1600.00 | 300.00 | 30 | | 7521 | WARD | SALESMAN | 7698 | 1981-02-22 | 1250.00 | 500.00 | 30 | | 7566 | JONES | MANAGER | 7839 | 1981-04-02 | 2975.00 | NULL | 20 | | 7654 | MARTIN | SALESMAN | 7698 | 1981-09-28 | 1250.00 | 1400.00 | 30 | | 7698 | BLAKE | MANAGER | 7839 | 1981-05-01 | 2850.00 | NULL | 30 | | 7782 | CLARK | MANAGER | 7839 | 1981-06-09 | 2450.00 | NULL | 10 | | 7788 | SCOTT | ANALYST | 7566 | 1987-07-13 | 3000.00 | NULL | 20 | | 7839 | KING | PRESIDENT | NULL | 1981-11-17 | 5000.00 | NULL | 10 | | 7844 | TURNER | SALESMAN | 7698 | 1981-09-08 | 1500.00 | 0.00 | 30 | | 7876 | ADAMS | CLERK | 7788 | 1987-07-13 | 1100.00 | NULL | 20 | | 7900 | JAMES | CLERK | 7698 | 1981-12-03 | 950.00 | NULL | 30 | | 7902 | FORD | ANALYST | 7566 | 1981-12-03 | 3000.00 | NULL | 20 | | 7934 | MILLER | CLERK | 7782 | 1982-01-23 | 1300.00 | NULL | 10 | | 8000 | zhangsan | CLERK | 7782 | 1982-01-23 | 1300.00 | NULL | 50 | +-------+----------+-----------+------+------------+---------+---------+--------+
mysql> begin; Query OK, 0 rows affected (0.00 sec) mysql> update emp set sal=0 where empno=7369; Query OK, 1 row affected (0.02 sec) Rows matched: 1 Changed: 1 Warnings: 0 mysql> rollback; Query OK, 0 rows affected (0.03 sec) mysql> select * from emp; +-------+----------+-----------+------+------------+---------+---------+--------+ | empno | ename | job | mgr | hiredate | sal | comm | deptno | +-------+----------+-----------+------+------------+---------+---------+--------+ | 7369 | SMITH | CLERK | 7902 | 1980-12-17 | 5000.00 | NULL | 20 | | 7499 | ALLEN | SALESMAN | 7698 | 1981-02-20 | 1600.00 | 300.00 | 30 | | 7521 | WARD | SALESMAN | 7698 | 1981-02-22 | 1250.00 | 500.00 | 30 | | 7566 | JONES | MANAGER | 7839 | 1981-04-02 | 2975.00 | NULL | 20 | | 7654 | MARTIN | SALESMAN | 7698 | 1981-09-28 | 1250.00 | 1400.00 | 30 | | 7698 | BLAKE | MANAGER | 7839 | 1981-05-01 | 2850.00 | NULL | 30 | | 7782 | CLARK | MANAGER | 7839 | 1981-06-09 | 2450.00 | NULL | 10 | | 7788 | SCOTT | ANALYST | 7566 | 1987-07-13 | 3000.00 | NULL | 20 | | 7839 | KING | PRESIDENT | NULL | 1981-11-17 | 5000.00 | NULL | 10 | | 7844 | TURNER | SALESMAN | 7698 | 1981-09-08 | 1500.00 | 0.00 | 30 | | 7876 | ADAMS | CLERK | 7788 | 1987-07-13 | 1100.00 | NULL | 20 | | 7900 | JAMES | CLERK | 7698 | 1981-12-03 | 950.00 | NULL | 30 | | 7902 | FORD | ANALYST | 7566 | 1981-12-03 | 3000.00 | NULL | 20 | | 7934 | MILLER | CLERK | 7782 | 1982-01-23 | 1300.00 | NULL | 10 | | 8000 | zhangsan | CLERK | 7782 | 1982-01-23 | 1300.00 | NULL | 50 | +-------+----------+-----------+------+------------+---------+---------+--------+
锁:
分为:InnoDB 行级锁, 只要两个客户端更新的是不同的行,互不干扰 。MyISAM 表锁,是锁住整个表。
在具体的语句中又分为X排他锁,S共享锁
X排他锁:一般加在修改语句上,当以有语句修该数据库中某个数据时加了X排他锁,其他语句不能访问此数据。
S共享锁:一般加在查询语句上,当以有语句查询数据库中某个数据时加了S共享锁,其他语句能查询此数据再加S共享锁,但是不能修改加X排他锁。
事物的隔离:
有不同的隔离级别, 隔离级别越低,并发性越好,但数据的一致性差 ,隔离级别越高,并发性差,但数据的一致性高
由低到高四种:读未提交 < 读提交 < 可重复读(mysql默认) < 序列化读错误的级别由高到低
脏读(读未提交) ,不可重复读,幻读脏读:比如一个数据初始值为100,在执行一组sql语句为事物中时,修改了这个数据为50。另一个事物语句想去访问数据,查出这个值为50使用了。此时前一个事物发现错误,rollbcak了,撤回了修改,数据有变成100,但是第二个事物使用的是50。
不可重复读:两个事物,一个查询,另一个做update操作,导致一个事务内多次查询结果不一致。
幻读:两个事物,一个查询,另一个做insert操作,插入了一条数据,第一个事物查询过后未查到特定的数据,第二个事物插入了这条特定的数据,此时第一个事物插入这个特定数据时又插不进去。
事物的四个特性:
原子性 A 多个sql要作为一个整体运行,不可分割
一致性 C 一个事务内结果应当一致
隔离性 I
持久性 D 事务一旦提交,事务内的修改就应当永久生效
其他sql总结 :
查看有哪些库: show databases;
查看库的创建语句: show create database 库名;
使用库: use 库名;
查看有哪些表: show tables;
查看表结构: desc 表名;
查看建表语句: show create table 表名;
\G 可以取代; 效果是把表行转列
查看系统变量的值: select @@系统变量名;select @@transaction_isolation; // 查看事务隔离级别
select @@port; // 查看服务器端口号
select @@character_set_server; // 查看默认字符集
select @@secure_file_priv;在创建数据库时用[if not exists] 判断表不存在时才创建, 如果已经存在,不执行任何操作
举例:创建student表时,如果表已经存在,就不会再创建,但是不会报错,如果是用scoure导入一系列sql语句时,后面的sql语句还会执行。
create table if not exists student( sid int primary key auto_increment, sname varchar(20) not null unique, birthday date, sex char(1) ) ;
sql语句中创建表时的约束条件:
not null 表示此列取值不能为空
unique 表示此列的取值是唯一的 (一张表可以有多个唯一约束)
primary key 同时起到了约束的效果, 唯一且非空(一张表只能定义一次)
foreign key 外键约束, 某一列的取值来自于另一张表(列必须是主键或唯一的)格式:foreign key (列名)references 表名(列名)
注意:外键总建在多的一方。