MYSQL基础02(查询)

查询是很大的一块,所以这里我只会写mysql的特点,就我目前使用的情况,MYSQL对标准SQL是比较支持,如果是新手的话,建议去w3school 学习标准SQL.

1.DUAL

DUAL是一个虚拟表,即该表是不存在的,用于直接select 标量时,使语句看起来符合sql规范

-- MSSQL
select 1,'A'
-- Oracle中dual 不可缺少
select 1,'A' from DUAL
-- mysql  以下2种格式都支持
select 1,'A';
select 1,'A' from DUAL;

2.LIMIT

相对MSSQL来说,MYSQL并没有TOP关键字,但有LIMIT,而且效率更高且更灵活

SELECT * FROM usr LIMIT 1;
-- LIMIT 1 的意思是取1条记录, MYSQL在取完1条记录后将不再操作.

SELECT * FROM usr LIMIT 0,2;
-- LIMIT 0,2的意思是从第一行(包括第一行)开始,取2条记录

SELECT * FROM usr WHERE u_id IN (SELECT u_id FROM usr WHERE dept='信息部' LIMIT 1);
-- 该语句执行时,MYSQL会报错,意思是不能在子查询中使用limit
-- 解决办法,将使用limit的语句再套一层表即可;如下:
SELECT * FROM usr WHERE u_id IN (SELECT * FROM (SELECT u_id FROM usr WHERE dept='信息部' LIMIT 1)aa)

PS:MSSQL中使用TOP,数据库会先排序,然后再返回数据,因此limit的效率比较高

3.子查询的update错误

UPDATE usr SET usr_name='匿名' WHERE u_id IN (SELECT u_id FROM usr WHERE dept='信息部')
-- 语句报错,大概意思是修改表不能使用自身
-- 解决方法,跟上面一样,再套一层表即可
UPDATE usr SET usr_name='匿名' WHERE u_id IN (SELECT * FROM (SELECT u_id FROM usr WHERE dept='信息部')aa)

 4.变量声明

mysql的查询语句中,变量不需要声明,直接赋值即可, @表示局部变量(仅在当前会话有效) @@表示全局变量

-- 使用set 赋值有以下2种方法
set @num=1;
set @num:=1;
-- 以下使用select 赋值
select @num:=1;
以上三种方法效果是一样的。

SELECT @num:=deptid FROM dept
-- 查询语句赋值

5.不报错机制

用了一段时间后,发现mysql中一大特点就是一些常规的错误情况往往不报错而正常运行。但是虽然正常运行,不过结果可能往往不是你想要的,所以我认为这并不是好事,正因为不报错,导致一些错误情况而不知道。

-- ①以0作除数
select 1/0   -- 结果为null
-- ②插入日期字段时,日期格式错误
insert into mytable(created_date) values('215-5-5')  -- 插入值为'0000-00-00 00:00:00'
-- ③group by
SELECT deptid,dname FROM dept GROUP BY dname;
SELECT deptid,MAX(dname) FROM dept GROUP BY dname;
-- 以上语句mssql中会报错,select的字段必须存在分组字段中,但是mysql会正确运行,至于这样的做法有什么意义,我现在还没明白
-- ④where条件中数据类型不一致
select * from bill where b_id='a';
-- 说明:b_id 为int,mssql中会先将'a'转换成数字,于是报错; 而mysql会运行通过
SELECT * FROM dept WHERE deptid=1;
-- 说明:deptid为varchar,mssql中会将1转换成字符'1';运行正确
-- 而mysql会将deptid中含有'1'的数据都会过滤出来,执行类似于 like 的操作;因此如果要得到正确的数据,必须确保与deptid的类型一致,如下:
SELECT * FROM dept WHERE deptid='1'
-- 最后强调在mysql中where 的条件语句中的左右字段类型必须相同,否则可能会得到你不想要的数据

 6.获取自增ID

MYSQL中自增ID有2种方法; 先执行插入语句,然后紧跟着执行以下语句

-- 使用全局变量@@IDENTITY,但是一般的程序应用中往往都会使用多个数据库连接会话,所以全局变量绝大部分情况是不合适的
SELECT @@IDENTITY
-- 使用LAST_INSERT_ID(), 该函数是针对当前连接会话获取最新插入的ID,所以更合适一般程序的使用.
SELECT LAST_INSERT_ID()

使用SELECT LAST_INSERT_ID() 好像没有问题,但是仍有讲究的地方;在程序开发的过程中要确保"插入语句"和"获取自增id"在同一个会话中执行紧贴着执行; 如果使用批量插入 insert into mytable(name) values('name1'),('name2')  那么LAST_INSERT_ID()只获取到第一条记录的id

 

posted @ 2015-10-16 00:39  sadkilo  阅读(439)  评论(2编辑  收藏  举报