1》查询语句的基本语法mysql
语法:
SELECT 属性列表
FROM 表名
[WHERE 条件表达式 1]
[GROUP BY 属性名1 [HAVING 条件表达式2]]
[ORDER BY 属性名2 [ASC | DESC]]
属性列表表示须要查询的字段名
表名表示指的表名
WHERE 表示指定查询的条件
GROUP BY 指定的字段进行分组
若是GROUP BY 子句后面带着HAVING关键字,那么只有知足条件2才能输出。正则表达式
2》在单表上查询数据:
v 列出表的全部字段
root@zytest 16:19>select order_num,order_date,cust_id from orders;
v 使用*查出单表全部字段
root@zytest 16:22>select * from orders;
v 查询指定的字段
在orders表中有3个字段,order_num、order_date、cust_id,咱们查询其中2个。
root@zytest 16:22>select order_num,order_date from orders;
v where查询指定记录
root@zytest 16:53>select * from orders where cust_id=10003;sql
*****比较
root@zytest 16:53>select * from orders where cust_id<=10003;小于或者等于
root@zytest 16:56>select * from orders where cust_id>=10003;大于或者等于
root@zytest 16:56>select * from orders where cust_id>10003;大于
root@zytest 16:56>select * from orders where cust_id<10003;小于
root@zytest 16:57>select * from orders where cust_id != 10003; 不等于
root@zytest 16:57>select * from orders where cust_id <> 10003;排除掉10003数据库
指定范围
root@zytest 16:57>select * from orders where cust_id between 10003 and 10004;
root@zytest 16:57>select * from orders where cust_id not between 10003 and 10004;
指定集合
root@zytest 16:57>select * from orders where cust_id in(10001,10004);
root@zytest 16:57>select * from orders where cust_id not in(10003,10004);
匹配字符
root@zytest 16:57>select * from orders where cust_id like ‘10001’;
root@zytest 16:57>select * from orders where cust_id not like ‘10001’;
是否为空值
root@zytest 16:57>select * from vendors where vend_state is null;
root@zytest 16:57>select * from vendors where vend_state is not null;
多条件查询
root@zytest 16:57>select * from orders where cust_id=10003 and order_num=20005;
root@zytest 16:57>select * from orders where cust_id=10003 or cust_id=10005;less
查询结果不重复(distinct)字段名
语法:select distinct 字段名
select distinct cust_id from orders;
查询结果进行排序
语法:order by 属性名 [ASC|DESC]
select distinct cust_id from orders where cust_id>10003 order by cust_id desc;
查询数据进行分组group by
语法:group by 属性名 [having 条件表达式][with rollup]
having用来限制分组后的显示,知足条件表达式的结果将被显示
with rollup 关键字将会在全部记录的最后加上一条记录,该记录是上面全部记录的总和.
group关键字一般和group_concat()函数一块儿使用.group_concat把每一个分组指定的字段值显示出来.函数
group by 使用having条件约束过滤having 跟where做用同样。可是having只能用于group by 。
select sex,count(sex),group_concat(name) from student group by sex having sex='女';
group by 多个字段进行分组
select sex,count(sex),group_concat(name) from student group by sex,user_id having sex='女';
group by 与with rollup一块儿使用
root@zytest 10:02>select sex,count(sex) from student group by sex;
得出了分组出来的数量。若是想获得分组出来的总和怎么办?
咱们后面再加上with rollup就能够得出。
root@zytest 10:02>select sex,count(sex) from student group by sex with rollup;
对单个字段进行普通分组
root@zytest 06:56>select * from student group by address;
结合group_concat()进行指定每一个分组的值
root@zytest 08:48>select sex,group_concat(name) from student group by sex;3d
使用limint限制查询结果的数量
root@zytest 10:07>select * from student where user_id >2 limit 2;code
3》使用集合函数查询数据:regexp
集合函数包括:
count() 用来统计记录的条数
sum() 用来计算字段的值和总数
avg() 用来计算字段的值的平均值
max() 用来查询字段的最大值
min() 用来查询字段的最小值
count()总计全部记录的条目总数
root@zytest 10:24>select count(*) from student;
sum字段值得总和
root@zytest 10:25>select sum(user_id) from student;
avg 取平均值
root@zytest 10:25>select avg(user_id) from student;
max()取字段值得最大值
root@zytest 10:27>select max(user_id) from student;
min()取字段值得最小值
root@zytest 10:28>select min(user_id) from student;
server
4》多表链接查询:
1>内链接
具备相赞成义的字段,才能够进行内链接:
root@zytest 15:56>select cust_name,cust_address,order_date from customers,orders
where customers.cust_id=orders.cust_id;
2>外链接
外链接包括左查询和右查询
select属性名列表
from 表名1 left | right join 表名2 on 表名1.属性名=表名2.属性名;
左链接查询:
能够查询出表名1里面全部的数据,而表名2只能查出匹配的记录。
如下例子:表名1=vendors(主表)表名2=products(匹配表)
root@zytest 17:42>select vendors.vend_id,prod_name,prod_price from vendors left join products on
vendors.vend_id=products.vend_id;
右链接查询
能够查询出表名2全部的记录。而表名1只能查出匹配记录。
如下例子:表名2=products(主表) 表名1=vendors(匹配表)
root@zytest 17:52>select products.vend_id,prod_name from vendors right join products on
vendors.vend_id=products.vend_id;
看不到1006?由于products里面没有1006,因此在vendors表中不匹配。这里用用vendors ID去匹配products。有则匹配。
复合查询:
在左链接或者右链接查询出来以后如何进一步过滤?
root@zytest 18:18>select products.vend_id,prod_name,vend_name,vendors.vend_id from vendors right
join products on vendors.vend_id=products.vend_id where products.prod_name='Safe';
在后面直接加where就好了。
5》子查询:
子查询时将一个查询语句内嵌到另个查询语句当中。内层查询的查询结果,能够为外层查询语句提供查询条件;
1>带IN关键字的子查询
insert into student values('10005','aaaaa','','aaaaaa');
insert into student values('10006','aaaaa','','aaaaaa');
insert into student values('10003','aaaaa','','aaaaaa');
root@zytest 18:40>select * from orders where cust_id in (select user_id from student);
root@zytest 18:55>select * from orders where cust_id in (select user_id from student) and cust_id>'10003';进一步过滤
6》合并查询:
有时候须要多个表进行合并数据。咱们使用union和union all,使用union时系统会将合并的结果去掉重复。而且显示。可是union all偏偏相反,不会去掉 重复,会把全部的内容所有显示出来;
root@zytest 19:06>select vend_id from vendors union select vend_id from products;
root@zytest 19:07>select vend_id from vendors union all select vend_id from products;
7》为表和字段取别名:
为表取别名:
select * from student aa where aa.user_id='1';
为字段取别名:
select user_id as alvinzeng from student;
mysql> select * from yy1 aa where aa.user_id=1;
+---------+-----------+
| user_id | user_name |
+---------+-----------+
| 1 | zhangsan |
+---------+-----------+
1 row in set (0.00 sec)
8》使用正则查看:
在咱们的mysql当中,照样可使用正则表达式来查询结果;
正则咱们使用关键字“regexp”来链接正则
select * from vendors where vend_name regexp '^An';以An开头的
select * from vendors where vend_city regexp 's$';以s结尾的
select * from vendors where vend_city regexp '.d';若是字符后面包含d
select * from vendors where vend_city regexp 'd.'; d后面包含的任意字符
select * from vendors where vend_city regexp '[London]';只要包含中括号里面任意一个字符的都会被显示出来
select * from vendors where vend_city regexp '[^Paris]';匹配除了Paris之外的全部字符,也就是说Paris将被过滤掉了。
select * from vendors where vend_state regexp 'MI|OH';匹配MI或者OH任意一个知足都会被显示出来。
select * from vendors where vend_state regexp 'M*';匹配以包含M后面的任何字符。
select * from vendors where vend_name regexp 'll+';表明多个字符前面或者后面的任何字符
select * from vendors where vend_city regexp 'd{1}';查询d出现过1次或者N次
select * from vendors where vend_city regexp 'd{1,3}';查询d出现过1次,最多出现3次,
=====================Mysql存储过程与存储函数=================
1》建立存储过程:
语法:
MySQL中,建立存储过程的基本形式以下:
1>CREATE PROCEDURE sp_name ([proc_parameter[,...]])
[characteristic ...] routine_body
create 是建立的的意思
procedure 是指的建立的类型是存储过程。
sp_name参数是存储过程的名称;
proc_parameter表示存储过程的参数列表;
characteristic参数指定存储过程的特性;
routine_body参数是SQL代码的内容,能够用BEGIN…END来标志SQL代码的开始和结束。
proc_parameter中的每一个参数由3部分组成。这3部分分别是输入输出类型、参数名称和参数类型。其形式以下:
[ IN | OUT | INOUT ] param_name type
其中,IN表示输入参数;OUT表示输出参数; INOUT表示既能够是输入,也能够是输出; param_name参数是存储过程的参数名称;type参数指 定存储过程的参数类型,该类型能够是MySQL数据库的任意数据类型。
说明:MySQL中默认的语句结束符为分号(;)。存储过程当中的SQL语句须要分号来 结束。为了不冲突,首先用"DELIMITER &&"将MySQL的结束符 设置为&&。最后再用"DELIMITER ;"来将结束符恢复成分号。这与建立触发器时是同样的。
2>存储过程和存储函数的区别:
存储过程和函数目的是为了可重复地执行操做数据库的SQL语句的集合,区别是写法和调用上:
写法上:存储过程的参数列表能够有输入参数,输出参数,能够输入输出参数。函数的参数列表只有输入参数,而且有return<返回值类型,无长度说 明>
在返回值上的区别:存储过程的返回值,能够有多个值,函数返回值,只有一个值;
举例1:
需求1、存储过程一(功能返回Mysql的版本号、用户、所在数据库、用户链接数、)
Delimiter &&
create procedure alvin1(
out getversion varchar(30),
out userversion varchar(30),
out userdatabase varchar(30),
out userconnection int)
reads sql data
begin
select version() into getversion;
select user() into userversion;
select database() into userdatabase;
select connection_id() into userconnection;
end &&
delimiter ;
call alvin1(@a,@b,@c,@d);
select @a,@b,@c,@d;
需求2、统计student id的数据量总共是多少?
create procedure alvin2(
out zycount int)
reads sql data
begin
select count(*) into zycount from student;
end&&
delimiter ;
call alvin2(@a);
select @a;
2》变量的使用:
在整个存储和函数中,能够定义和使用变量,用户可使用declare关键字来定义变量,而后能够为变量赋值,这些变量的做用范围是begin…end程序 中。
1>定义变量
declare aa_id int default 10;
2>为变量赋值
set aa_id=1001;
IN参数例子:
root@zytest 23:15>delimiter &&
root@zytest 23:16>create procedure alvin1( #建立一个名字为alvin1存储过程
-> in p_in int) #设置传入的参数类型和变量
-> begin
-> select p_in; #查询第一次传进来的参数
-> set p_in=2; #:从新给p_in 赋值后。覆盖掉传进来的参数值
-> select p_in; #:在查询一次赋值
->end&&
root@zytest 23:19>delimiter ;
root@zytest 23:19>set @p_in=1;#开始传入参数赋值
root@zytest 23:19>call alvin1(@p_in);#调用存储过程
+------+
| p_in |
+------+
| 1| #传入的值为1,
+------+
1 row in set (0.03 sec)
+------+
| p_in |
+------+
| 2 | #过程中的二次赋值
+------+
1 row in set (0.03 sec)
Query OK 0 rows affected (0.03 sec)
root@zytest 23:20>select @p_in; #查询外边传参赋值的结果
+-------+
| @p_in |
+-------+
| 1 |
+-------+
OUT参数例子:
root@zytest 23:41>delimiter &&
root@zytest 23:41>create procedure name_info(建立一个名称为name_info的存储过程
-> out p_out int) #定义输出的变量和数据类型
-> begin
-> select p_out; #查看输出参数
-> set p_out=2; #给参数赋值
-> select p_out; #查询赋值结果
->end&&
Query OK, 0 rows affected (0.00 sec)
root@zytest 23:42>delimiter ;
root@zytest 23:42>set @p_out=1; #传入一个参数。看看是否会在call调用的时候显示出来?
Query OK, 0 rows affected (0.00 sec)
root@zytest 23:42>call name_info(@p_out);
+-------+
| p_out |
+-------+
| NULL | #传入的参数为空
+-------+
1 row in set (0.01 sec)
+-------+
| p_out |
+-------+
| 2 | #存储函数里面赋值的参数调用成功
+-------+
1 row in set (0.01 sec)
root@zytest 23:42>select @p_out;
+--------+
| @p_out |
+--------+
| 2 | #:只看到存储函里面赋值的。传入的参数无效。
+--------+
1 row in set (0.00 sec)
INOUT参数列子:
root@zytest 00:03>delimiter &&
root@zytest 00:03>create procedure alvin_name( #建立一个名为alvin_name的函数
-> inout p_inout int) #建立一个能够传入和传出的p_inout的变量和数据类型
-> begin
-> select p_inout; #:查询传入的数据
-> set p_inout=2; #:给p_inout的赋值
-> select p_inout; #:在此查询p_inout的值
->end&&
root@zytest 00:04>delimiter ;
root@zytest 00:04>set @p_inout=1; #:开始传入参数
Query OK, 0 rows affected (0.00 sec)
root@zytest 00:04>call alvin_name(@p_inout); #:开始调用
+---------+
| p_inout |
+---------+
| 1 | #使用inout既能够传入能够传出
+---------+
1 row in set (0.00 sec)
+---------+
| p_inout |
+---------+
| 2 | #使用inout既能够传入能够传出
+---------+
1 row in set (0.00 sec)
root@zytest 00:04>select @p_inout; #查询最后结果
+----------+
| @p_inout |
+----------+
| 2 | #:能够传出也能够传入,最终返回结果为2,
+----------+
1 row in set (0.00 sec)
3》建立存储函数:
语法:create function sp_name([func_parameter[,…….]])
Returns type
[characteristic…]routine_body。
其中,sp_name参数是存储函数的名称。
Func_parameter 表示存储函数的参数列表。
Returns type 指定返回的参数类型。
characteristic参数指定存储函数的特性。
routine_body参数是SQL代码的内容。
能够用BEGIN…END来标志 SQL代码开始和结束。
create function 函数名(参数1 数据类型[,参数2 数据类型,参数3 数据类型])returns 返回值类型
begin
任意系列的sql语句;
return 返回值;
end;
注:与储存过程不一样
一、参数只有输入型
二、向调用方返回结果值
常见的错误:
This function has none of DETERMINISTIC, NO SQL解决办法
建立存储过程时
出错信息:
ERROR 1418 (HY000): This function has none of DETERMINISTIC, NO SQL, or READS SQL DATA in its declaration and binary logging is enabled (you *might* want to use the less safe log_bin_trust_function_creators variable)
其中在function里面,只有 DETERMINISTIC, NO SQL 和 READS SQL DATA 被支持。若是咱们开启了 bin-log, 咱们就必须为咱们的function指定一个参数。
解决方法:
SQL code
mysql> show variables like 'log_bin_trust_function_creators';
+---------------------------------+-------+
| Variable_name | Value |
+---------------------------------+-------+
| log_bin_trust_function_creators | OFF |
+---------------------------------+-------+
mysql> set global log_bin_trust_function_creators=1;
mysql> show variables like 'log_bin_trust_function_creators';
+---------------------------------+-------+w
| Variable_name | Value |
+---------------------------------+-------+
| log_bin_trust_function_creators | ON |
+---------------------------------+-------+
这样添加了参数之后,若是mysqld重启,那个参数又会消失,所以记得在my.cnf配置文件中添加:
log_bin_trust_function_creators=1
举列:根据输入的vend_id查询到每一个用户的vend_name。
delimiter&&
create function alvin11( #建立一个函数名称为alvin11
bb_id int)#定义一个参数类型和它的数据类型
returns varchar(20)#定义下面vend_name的返回数据类型
begin # 开始
return (select vend_name from vendors#返回 SQL语句查询的结果,
where vend_id=bb_id);
end && #结束
delimiter ;#跳出整体段落。
select alvin11(1001);#调用存储函数-查询结果
4》流程控制:
1>存储过程if语句使用方法:
delimiter&&
create procedure zy_if(in aa int,out bb int)
begin
if aa>20 then
set bb=30;
elseif aa=20
then
set bb=20;
else
set bb=15;
end if;
end&&
delimiter ;
开始调用1 aa=20
call zy_if(20,@bb);
select @bb;
开始调用2 aa=25
call zy_if(25,@bb);
select @bb;
开始调用3 aa=15
call zy_if(15,@bb);
select @bb;
2>存储过程case用法
delimiter&&
create procedure zy_case(in aa int,inout bb int)
begin
case
when aa=20 then set bb=20;
when aa>20 and aa<=50 then set bb=30;
when aa>51 then set bb=60;
else set bb=15;
end case;
end&&
delimiter ;
开始调用验证1
call zy_case(20,@bb);
select @bb;
开始调用验证2
call zy_case(21,@bb);
select @bb;
开始调用验证3
call zy_case(52,@bb);
select @bb;
开始调用验证4
call zy_case(10,@bb);
select @bb;
3>存储过程 while 循环使用,插入1万条数据
delimiter&&
create procedure zy_while()
begin
declare count int default 0;
while count < 10000 do
insert into zybb (user_id,name)values(count,'aa1');
set count = count + 1;
end while;
end&&
delimiter ;
call zy_while();调用存储过程
5》调用存储过程和函数:
1>调用方式call +存储过程名称+参数
如:call alvin_name(@p_inout);
2>查询结果
select @p_inout
6》查看存储过程和函数:
1>查询存储过程
show procedure status;
查询某具体存储过程详细
show create procedure alvin1\G;
2>查询存储函数
show function status;
查询某个具体存储函数详细
show create function alvin10\G;
7》删除存储过程和函数:
1>删除存储过程 drop procedure alvin1; 2>删除存储函数 drop function alvin1;