mysql 复习笔记
dql 语言 +号的作用 mysql 中+ 只有一种作用 就是加法 如果字符 + 数字转换为数字型计算 如果转换失败 把字符型数值转换为0 select null+10 只要有null + 任何形态 结果为null (貌似乘除都是那样) in 简单用法i(类型必须统一)和 or 效率上没有区别 -- is null 使用 select * from myemployees.employees where commission_pct is not null; -- 不能用= -- 安全等于 <=> 也可以类似于= select * from myemployees.employees where commission_pct <=> null; select * from myemployees.employees where commission_pct <=> '0.2'; -- is null 只能判断 null <=>可以判断空 和 普通数值 -- like '%%'; 相当于把 null去掉了 只要那个是非空字段都会显示 select * from myemployees.employees where commission_pct like '%%'; 非等值连接 略 等值连接 也就是咱们常用的 inner join 自连接 把一张表当成 两张表或者更多表使用 进行连接 例如:获取员工的上级名称 (领导和员工 都在一张表里面) select yuangong.manager_id , yuangong.last_name 员工名称 , lingdao.last_name 领导名称 ,lingdao.employee_id from employees yuangong ,employees lingdao where yuangong.manager_id=lingdao.employee_id ; sql 连接 sql99语法 发现公司用92的比较多 /* 分类 join 前面不写类型默认是inner join 内连接 :【连接类型】 inner join 不加inner 默认内连接 这个于sql92 实现是一样的 外连接 左外 left [out] join out 加不加一样 右外 right [out] join 全外 full join 交叉 cross join 就是笛卡尔积 就是直接逗号隔开 不写条件那种。 三表关联如下 select * from emp e inner join dept d on e.deptno = d.deptno inner join city c on d.loc =c.cid where e.sal>2000 or e.comm is not null order by e.sal */ select * from employees e inner join departments on e.department_id = departments.department_id; -- 外连接 用于查询一个表中有另一个表没有的东西记录 内连接是查询两个表都有(并集) /* 外连接 分主表和从表 如果从表有数据和主表匹配会显示出来 如果没有 主表也会显示出来 但对应从表数据为空 类似于 外连接内容=内连接内容 + 主表未和从表匹配的内容 主表和从表怎么分 ? (看是左还是右连接 左连左边为主 右连接右边为主 一般数据多的为主表 这样数据多的和数据少的匹配起来 肯定有数据多的剩下 ) 这个要看左右外连接 左外连接(left join)左边是主表 右外连接(right join) 右边是主表 左外和右外交换两个表顺序可以实现相同效果 全外连接就是两个表类似于左外和右外 只不过 类似于 左边和右边都是主表(mysql不支持) 全外连接=内连接+表1有表二没有的+ 表二有表一没有的 */ 例如 :查询男朋友不在男神表的女生名 select * from beauty left join boys on boyfriend_id=boys.id where boys.id is null; 其实左右连接都能实现看你怎么连接。 关于exists关键字 exists关键字表示存在。使用exists关键字时,内层查询语句不返回查询的记录,而是返回一个真假值。 如果内层查询语句查询到符合条件的记录,就返回一个真值(true)(注意了有数据就是真),否则,将返回一个假值(false): 当返回的值为true时,外层查询语句将进行查询; 当返回的值为false时,外层查询语句将不进行查询或者查询不出任何记录。 -- 列举一下错误用法 比如你要找 id=1003的所有员工信息 你不能这样写 select * from employee where exists (select d_name from department where d_id=1003); 因为 1003 员工存在所以返回是true 这里不单单指d_name不为空是指有一条数据就行 所以 d_name可以换为 * ,1 ,2 ,之类的。 常用函数 : count(字段名) select count(*) from employees;-- 查询表的总行数固定写法 (除非所有列同时为null) select count(2) from employees; -- select(1) 相当于增加了一列都是1 2 都是一样的 其中count(*)和count(1)效率差不多 比count(字段要高) isnull(字段名) 判断某字段 是否为 null 如果是空返回1 ifnull(字段名称,返回值) 如果字段为空返回 返回值 ABS(x) 返回x的绝对值 PI()返回圆周率π,默认显示6位小数 MOD(x,y)返回x被y除后的余数 CEIL(x)、CEILING(x)返回不小于x的最小整数 ROUND(x)、ROUND(x,y) 前者返回最接近于x的整数,即对x进行四舍五入;后者返回最接近x的数,其值保留到小数点后面y位,若y为负值,则将保留到x到小数点左边y位 POW(x,y)和、POWER(x,y)返回x的y次乘方的值 LENGTH(str) 计算字符串字符个数 数字不行 CONCAT(s1,s2,...)返回连接参数产生的字符串,一个或多个待拼接的内容,任意一个为NULL则返回值为NULL CONCAT_WS(x,s1,s2,...)返回多个字符串拼接之后的字符串,即s1+x+s2 LOWER(str)和LCASE(str)、UPPER(str)和UCASE(str)前两者将str中的字母全部转换成小写,后两者将字符串中的字母全部转换成大写. LEFT(s,n)、RIGHT(s,n)前者返回字符串s从最左边开始的n个字符,后者返回字符串s从最右边开始的n个字符。 LTRIM(s)、RTRIM(s)前者返回字符串s,其左边所有空格被删除;后者返回字符串s,其右边所有空格被删除 TRIM(s)返回字符串s删除了两边空格之后的字符串 TRIM(s)d返回字符串s删除了两边空格之后的字符串 REPEAT(s,n)返回一个由重复字符串s组成的字符串,字符串s的数目等于n REPLACE(s,s1,s2)返回一个字符串,用字符串s2替代字符串s中所有的字符串s1 STRCMP(s1,s2)若s1和s2中所有的字符串都相同,则返回0;根据当前分类次序,第一个参数小于第二个则返回-1,其他情况返回1 REVERSE(s)将字符串s反转 select instr('杨不悔尹柳霞爱上了尹柳霞','尹柳霞'); -- 返回子串尹柳霞第一次出现的索引 substr 或者 substring select substr('我日你的妈妈',5); -- 输出妈妈 截取5后的字符 下标从1开始 select substr('我日你的妈妈',2,4) O; -- 输出日你的妈 截取 从2开始往后数4个字符包含2 -- truncate (); 截断函数 select truncate (1.69,1); -- 从小数点第一个截断 注意不是四舍五入 now()日期函数select now(); -- 2020-12-31 15:42:07 curdate(); select curdate(); -- 只返回data year()month()day() 获取时间的特定内容年月日 其中里面可以填的字符串为'2020-12-31 15:42:07' 这种形式或者/也可以 monthname() 获取月的名称英文的 select str_to_date('4-3 1992','%m-%d %Y') 把特定字符串转为时间日期型 date_format() 日期转 指定 字符串select date_format(now(),'%Y/%m/%d'); datediff('2021-01-09 13:51:38','2021-01-08 13:51:30'); 计算这两个日期的时间差 timestampdiff(SECOND,'2020-01-08 13:51:30',now()); 计算这两个时间相差秒数 ADDTIME('2020-01-08 13:51:30',11) 返回相加后的时间 后面那个是秒数 SUBTIME(date,expr) 返回相减后的时间 后面那个是秒数。 流程控制 if(条件,返回值成立结果,返回值不成立结果) /* case 常量或者表达式(貌似这个case后面的加不加都一样) when 常量1 then 要显示的值或者语句 when 常量2 then 要显示的值或者语句 ... else 要显示的值或者语句 end as xx from xx */ 例如 SELECT department_id,salary , CASE department_id WHEN department_id%2=0 THEN salary*99 WHEN department_id%2=1 THEN salary*1.2 ELSE salary END as 新 FROM employees; /* case (注意这个后面没有东西) when 条件1 then 要显示的值或者语句 when 条件2 then 要显示的值或者语句 else end as xxx from xx */ select * , case when salary>20000 then 'A' when salary>15000 then 'B' when salary>10000 then 'c' else 'D' end as 级别 from employees;