天天看點

Python學習第十八天——MySQL表關系判斷、查詢關鍵字、多表查詢

表關系判斷:

​ 表關系分類:

​ 1.一對多

​ 2.多對多

​ 3.一對一

​ 4.沒有關系

​ 表關系的判斷:

​ 思想:換位思考

​ 一對多:

​ 外鍵字段建在多的一方。

​ 1.以員工表與部門表為例:

​ 1.先站在員工表角度

​ 問:一個員工能否對應多個部門

​ 答:不可以

​ 2.再站在部門表角度

​ 問:一個部門能否對應多名員工

​ 答:可以

​ 結論:兩邊一個可以,一個不可以,那麼表關系就是一對多。

​ SQL語句實作:

​ 1.先建立基本字段

​ 2.在考慮外鍵字段

​ create table emp(

​ id int primary key auto_increment,

​ emp_name varchar(32),

​ emp_salary int,

​ dep_id int,

​ foreign key(dep_id) references dep(id)

​ );

​ create table dep(

​ id int primary key auto_increment,

​ dep_name varchar(32),

​ dep_desc varchar(64)

​ );

​ 注意:

​ 1.在建立表時先建立被關聯的表(沒有外鍵字段的表)。

​ 2.在錄入資料的時候,先錄入被關聯表的資料。

​ 3.修改或删除被關聯的資料,沒法做修改。

​ 級聯更新級聯删除SQL實作:

​ create table emp(

​ id int primary key auto_increment,

​ emp_name varchar(32),

​ emp_salary int,

​ dep_id int,

​ foreign key(dep_id) references dep(id)

​ on update cascade #級聯更新

​ on delete cascade #級聯删除

​ );

​ create table dep(

​ id int primary key auto_increment,

​ dep_name varchar(32),

​ dep_desc varchar(64)

​ );

​ 多對多

​ 針對多對多關系,外鍵字段并不會建在任何一張表,而是單獨開設一張新表,單獨存儲

​ SQL實作:

​ create table book(

​ id int primary key auto_increment,

​ title varchar(32),

​ price float(8,2)

​ );

​ create table book(

​ id int primary key auto_increment,

​ title varchar(32),

​ price float(8,2)

​ );

​ create table booktoauthor(

​ id int primary key auto_increment,

​ author_id int,

​ foreign key(author_id) refrenxes author(id)

​ on update cascade

​ on delete cascade,

​ book_id int,

​ foreign key(book_id) references book(id)

​ on update cascade

​ on delete cascade

​ );

​ 一對一

​ 以使用者表與使用者詳情表為例

​ 先站在使用者表角度

​ 問:一名使用者能否對應多個使用者詳情

​ 答:不可以

​ 再站在使用者詳情表角度:

​ 問:一個使用者詳情是否能對應多名使用者

​ 答: 不可以

​ 針對一對一關系,外鍵字段建在任何一方都可以,但是推薦你建立在查詢頻率較高的表中。

​ SQL實作:

​ create table userinfo(

​ id int primary key auto_increment,

​ name varchar(32),

​ age int,

​ detail_id int unique, #設定唯一索引建立一對一關系

​ foreign key(detail_id) references userinfo_detail(id)

​ on update cascade

​ on delete cascade

​ );

查詢關鍵字

​ 1.select

​ 用來指定表的字段資料

​ select * from emp;

​ select id, name from emp;

​ 在工作中一般很少使用*。

​ 2.from

​ 後面跟需要查詢的表名。

​ 3.where 篩選資料

​ 1.查詢id大于等于3,小于等于6的資料

​ select id ,name from emp where id >=3 and id <= 6;

​ select id ,name from emp where id between 3 and 6;

​ 2.查詢薪資是20000或18000或17000的資料

​ select * from emp where salary = 20000 or salary = 18000 or salary = 17000;

​ select * from emp where salary in (20000,18000,17000);

​ 模糊查詢:

​ 關鍵字 like

​ 關鍵符号:

​ %:比對任意個數的任意字元

​ _:比對單個個數的任意字元

​ 3.查詢姓名中帶有字母o的員工姓名和薪資

​ select name,salary from emp where name like ‘%o%’;

​ 4.查詢姓名中有四個字元組成的員工姓名和薪資

​ select name,salary from emp where name like ‘____’;

​ select name,salary from emp where char_length(name) = 4;

​ 5.查詢id小于3或者大于6的資料

​ select * from emp where id not between 3 and 6;

​ 6.查詢薪資不在20000,18000,17000範圍的資料

​ select * from emp where salary not in (20000,18000,17000);

​ 7.查詢崗位描述為空的員工與崗位名 針對null不能用等号,隻能用is

​ select name,post from emp where post_comment is NULL;

​ select name,post from emp where post_comment is not NULL;

​ 4.group by 分組

​ 分組

​ 将單個單個的個體按照指定條件分成一個個整體。

​ 分組之後預設隻能擷取分組的依據,其他字段無法在直接擷取(可以間接擷取)

​ 但是5.6需要手動開啟嚴格模式

​ set global sql_mode = ‘STRICT_TRANS_TABLES,PAD_CHAR_TO_FULL_LENGTH,ONLY_FULL_GROUP_BY’

​ 聚合函數

​ 分組之後頻繁需要使用的

​ max 最大值

​ min 最小值

​ sum 求和

​ count 計數

​ avg 平均值

​ 1.每個部門的最高工資

​ select post,max(salary) from emp group by post;

​ 2.每個部門的最低工資

​ select post,min(salary) from emp group by post;

​ 3.每個部門的平均薪資

​ select post,avg(salary) from emp group by post;

​ 4.每個部門的人數

​ select post,count(id) from emp group by post;

​ 5.每個部門的月工資總和

​ select post,sum(salary) from emp group by post;

​ 可以使用as起别名,也可以給表起别名

​ select post as ‘部門’,sum(salary) as ‘總和’ from emp group by post;

​ 檢視分組之後的部門名稱和每個部門下所有的員工姓名

​ group_count() 擷取分組以外的字段資料,并且支援拼接操作

​ select post,group_concat(name) from emp group by post;

​ select post,group_concat(name,’:’,salary) from emp group by post;

​ concat() 未分組之前使用的拼接功能

​ select concat(name,’:’,sex) from emp;

​ concat_ws()

​ select concat_ws(’:’,name,sex,salary,age) from emp;

​ group_concat(name,’:’,salary) 擷取分組以外的字段資料,

​ 5.having 過濾

​ 功能上having與where是一樣的,但是使用位置上有所不同

​ where在分組之前使用,having在分組之後使用。

​ 舉例:

​ 統計各部門年齡在30歲以上的員工

​ 1.先篩選出所有30歲以上的員工

​ select * from emp where age>30;

​ 2.然後再按照部門分組

​ select post,avg(salary) from emp where age>30 group by post;

​ 3.分組之後做過濾操作

​ select post,avg(salary) from emp

​ where age>30

​ group by post

​ having avg(salary)>10000;

​ 6.distinct 去重

​ 帶有主鍵的資料肯定無法去重

​ select distinct age from emp;

​ 7.order by 排序

​ 預設升序 關鍵字 asc

​ 降序排序 關鍵字 desc

​ select * from emp order by salary desc;

​ 指定多個字段

​ select * from emp order by age desc,salary asc;

​ 統計各部門年齡在20歲以上的員工的平均工資,并且保留平均高工資大于1000的部門,然後對平均工資進行排序。

不在代碼行敲的代價,未知原因報錯就是不行,後來也不知道為什麼就又好了,神。

select post,avg(salary) from emp

where age>20

group by post

having avg(salary)>1000

order by avg(salary) desc;

在代碼行敲的就可以。

select post,avg(salary) from emp
	where age>20
	group by post
	having avg(salary)>1000
	order by avg(salary) desc;
           

8.limit 分頁

​ 用來限制資料的顯示:

​ select * from emp limit 5,5;

# 查詢工資最高的人的詳細資訊,先按照工資排序,然後限制展示條數
select * from emp order by salary desc limit 1;
           

​ 9.regexp 正則

​ 正規表達式 用一些特殊複合的組合篩選出符合條件的資料

select * from emp where name regexp '^j.*(n|y)$';
	# '^j.*(n|y)$'  j開頭 中間無所謂 n或者y結尾
           

多表查詢的思想

1.子查詢

​ 分布解決問題

​ 将一條SQL語句的查詢結果用括号括起來,作為另一條語句的查詢條件。

​ select * from dep where id in (select dep_id from emp where name=‘jason’)

2.連表操作

​ 前戲(了解)

​ select * from emp,dep

​ 基于上表篩選資料

​ 為了避免字段沖突可以在字段名前加表名明确。

​ select * from emp,dep where emp.dep_id = dep.id

​ 現将所有需要用到的表拼接到一起(一張表)

​ 然後就是轉換成單表查詢

​ 連表操作:

​ inner join 内連接配接 連接配接公共部分

​ select * from emp inner join dep on emp.dep_id=dep.id;

​ left join 左連接配接 以左表為基準展示所有資料,沒有的null填充

​ select * from emp left join deo on emp.dep_id=dep.id;

​ right join 右連接配接 以右表為基準展示所有資料,沒有的null填充

​ select * from emp right join deo on emp.dep_id=dep.id;

​ union 全連接配接 以所有表為基準展示所有資料,沒有的null填充

​ select * from emp left join deo on emp.dep_id=dep.id

​ union

​ select * from emp right join deo on emp.dep_id=dep.id;

建議:在書寫SQL語句的時候一定不要想着一次成功,寫一點看一點再寫一點,慢慢拼湊起來

表字段操作的補充

​ 1.添加表字段

​ alter table t_name add age int; #預設尾部追加

​ alter table t_name add gender enum(‘male’,‘female’) after age; #指定追加位置

​ alter table t_name add 字段名 字段類型 first #追加在開頭

​ 2.修改字段

​ modify隻能改字段資料類型完整限制,不能改字段名,但是change可以

​ ALTER TABLE 表名 MODIFY 字段名 資料類型 [完整性限制條件…];

​ ALTER TABLE 表名 CHANGE 舊字段名 新字段名 資料類型 [完整性限制條件…];

3.删除字段

ALTER TABLE 表名 DROP 字段名;