1.LeetCode 175
主要學(xué)習(xí)Left Join的用法
SQL LEFT JOIN 關(guān)鍵字
LEFT JOIN 關(guān)鍵字會從左表 (table_name1) 那里返回所有的行,即使在右表 (table_name2) 中沒有匹配的行。
題目大意
表Person:
| Column Name | Type |
|---|---|
| PersonId | int |
| FirstName | varchar |
| LastName | varchar |
PersonId is the primary key column for this table.
表: Address
| Column Name | Type |
|---|---|
| AddressId | int |
| PersonId | int |
| City | varchar |
| State | varchar |
AddressId is the primary key column for this table.
將表Person和Address合并,并返回FirstName, LastName, City, State,如果某一個人不存在city,State的信息,在相對應(yīng)的位置上也要標(biāo)為NULL值。
這里就需要用到left join來解決,因為一定保證的是Person的信息都必須存在,Address上對應(yīng)不存在的信息可以賦上NULL值,left join的使用往往需要加上條件限制ON
SELECT FirstName,LastName,City,State
FROM person s1 LEFT JOIN address s2 ON s1.PersonId = s2.PersonId
2.LeetCode 176
主要學(xué)習(xí)取最大值和limit的用法
| Id | Salary |
|---|---|
| 1 | 100 |
| 2 | 200 |
| 3 | 300 |
最后希望得到的是第二大的工資,如果不存在返回NULL
這上方的樣例應(yīng)該是返回
| SecondHighestSalary |
|---|
| 200 |
標(biāo)準(zhǔn)的解答如下所示:
SELECT max(Salary) as SecondHighestSalary
FROM Employee
WHERE Salary < (SELECT max(Salary) FROM Employee)
先獲取到所有小于最大值的值,再獲取其中的最大值,這樣即使是不存在也會返回NULL。
但是如果題目不要求一定要返回NULL,可以如下寫:
SELECT Salary as SecondHighestSalary
from Employee
order by Salary ASC
limit 1,1
從小到大排序,然后獲取第二行的數(shù)據(jù),這里limit 1,1就表示從下標(biāo)為1的行開始取1行數(shù)據(jù)
2.LeetCode 181
主要學(xué)習(xí)表的合并方法
對于表Employee:
| Id | Name | Salary | ManagerId |
|---|---|---|---|
| 1 | Joe | 70000 | 3 |
| 2 | Henry | 80000 | 4 |
| 3 | Sam | 60000 | NULL |
| 4 | Max | 90000 | NULL |
根據(jù)ManagerId可以看出3號Sam是Joe的管理者,4號Max是Henry的管理者,這里找到所有比自己管理者工資高的員工的名字
所以這個例子應(yīng)該返回
| Employee |
|---|
| Joe |
簡單的理解就是,將員工的信息和對應(yīng)的管理人員的信息合并到同行來比較工資大小,下面兩種簡單的寫法
select s1.name
from Employee as s1 join Employee as s2 #將兩個同樣的表合并,但保證是員工和其管理者對應(yīng)到同一行
where s1.ManagerId = s2.Id and s1.salary>s2.salary
select s1.name as Employee
from Employee as s1 join Employee as s2 on (s1.ManagerId = s2.Id) #將兩個同樣的表合并,但保證是員工和其管理者對應(yīng)到同一行
where s1.salary>s2.salary
2.LeetCode 182
主要學(xué)習(xí)having, group by , in的用法
Having語句
在 SQL 中增加 HAVING 子句原因是,WHERE 關(guān)鍵字無法與合計函數(shù)一起使用。合計函數(shù)比如SUM,COUNT,AVERAGE等
GROUP BY 語句
GROUP BY 語句用于結(jié)合合計函數(shù),根據(jù)一個或多個列對結(jié)果集進(jìn)行分組。
IN 操作符
IN 操作符允許我們在 WHERE 子句中規(guī)定多個值。
SQL IN 語法
SELECT column_name(s)
FROM table_name
WHERE column_name IN (value1,value2,...)
對于表Person:
| Id | |
|---|---|
| 1 | a@b.com |
| 2 | c@d.com |
| 3 | a@b.com |
找到所有重復(fù)了的Email
select email from Person group by email having count(*) > 1
如果進(jìn)行簡單擴展找到所有出現(xiàn)了重復(fù)郵箱的行的信息,那么對于上面這個sample來說就是輸出
| 1 | a@b.com |
| 3 | a@b.com |
那么只要在這句代碼基礎(chǔ)上進(jìn)行in操作的添加
select * from Person
where email in
(select email from Person group by email having count(*) > 1)
2.LeetCode 183
主要學(xué)習(xí)表基礎(chǔ)合并的用法
存在表customers和orders:
| Id | Name |
|---|---|
| 1 | Joe |
| 2 | Henry |
| 3 | Sam |
| 4 | Max |
| Id | CustomerId |
|---|---|
| 1 | 3 |
| 2 | 1 |
找到不是任何人customer的用戶名字,這里根據(jù)orders表可以看出1號用戶有顧客3(Sam) , 2號用戶有顧客4(Max)
也就是說只有Henry和Max不是任何人的客戶,所以輸出二者的名字
| Customers |
|---|
| Henry |
| Max |
select customers.`Name` as Customers
from
customers left join orders on (customers.Id = orders.CustomerId)
where
orders.Id is null
SELECT A.Name from Customers A
WHERE NOT EXISTS (SELECT 1 FROM Orders B WHERE A.Id = B.CustomerId)
SELECT A.Name from Customers A
LEFT JOIN Orders B on a.Id = B.CustomerId
WHERE b.CustomerId is NULL
SELECT A.Name from Customers A
WHERE A.Id NOT IN (SELECT B.CustomerId from Orders B)
2.LeetCode 183
主要學(xué)習(xí)sql函數(shù)的用法
對于Employee表:
| Id | Salary |
|---|---|
| 1 | 100 |
| 2 | 200 |
| 3 | 300 |
函數(shù)傳入一個N,找到不重復(fù)的工資排名第N位的工資
CREATE FUNCTION getNthHighestSalary(N INT) RETURNS INT
BEGIN
DECLARE M INT;
SET M = N-1;
RETURN (
# Write your MySQL query statement below.
SELECT DISTINCT salary as getNthHighestSalary #distinct保證工資是不重復(fù)的
from employee
ORDER BY salary DESC
limit M,1
);
END;
SELECT getNthHighestSalary(2); #這句話不加在提交代碼中,用來自己測試運行
1.LeetCode 178
主要學(xué)習(xí)select語句嵌套查詢的用法
| Id | Score |
|---|---|
| 1 | 3.50 |
| 2 | 3.65 |
| 3 | 4.00 |
| 4 | 3.85 |
| 5 | 4.00 |
| 6 | 3.65 |
將上述表Scores根據(jù)成績排名由大到小得到如下的結(jié)果
| Score | Rank |
|---|---|
| 4.00 | 1 |
| 4.00 | 1 |
| 3.85 | 2 |
| 3.65 | 3 |
| 3.65 | 3 |
| 3.50 | 4 |
SELECT
Score , (SELECT count(DISTINCT Score) FROM scores where Score>=s.score) Rank
from
scores s
ORDER BY Rank ASC
1.LeetCode 180
sql語句基本練習(xí)
| Id | Num |
|---|---|
| 1 | 1 |
| 2 | 1 |
| 3 | 1 |
| 4 | 2 |
| 5 | 1 |
| 6 | 2 |
| 7 | 2 |
在上表Logs找到連續(xù)三個數(shù)字都相同的數(shù)字,那么在這個樣例中就是1,可得
| ConsecutiveNums |
|---|
| 1 |
1.#將三個表做連接,來定義規(guī)則保證三者是連續(xù)相等的數(shù)字
SELECT
DISTINCT l1.Num as ConsecutiveNums
FROM
Logs l1 , Logs l2 , Logs l3
WHERE
l1.Num = l2.Num AND l1.Num = l3.Num
AND l1.Id = l2.Id-1
AND l2.Id = l3.Id-1
2.
SELECT D.Name AS Department ,E.Name AS Employee ,E.Salary
from
Employee E,
Department D
WHERE E.DepartmentId = D.id
AND (DepartmentId,Salary) in
(SELECT DepartmentId,max(Salary) as max FROM Employee GROUP BY DepartmentId)
1.LeetCode 178
主要學(xué)習(xí)date類型的用法
| Id(INT) | Date(DATE) | Temperature(INT) |
|---|---|---|
| 1 | 2015-01-01 | 10 |
| 2 | 2015-01-02 | 25 |
| 3 | 2015-01-03 | 20 |
| 4 | 2015-01-04 | 30 |
在這個weather表中找到比前一天溫度高的日子的id,這里應(yīng)該返回2,4,如下:
| Id |
|---|
| 2 |
| 4 |
select
B.Id
from
weather A , weather B
where
A.Temperature<B.Temperature and TO_DAYS(B.Date)-TO_DAYS(A.Date) = 1
1.LeetCode596
主要學(xué)習(xí)having下的函數(shù)比較作為限制條件的用法
對函數(shù)產(chǎn)生的值來設(shè)定條件,舉例來說,我們可能只需要知道哪些店的營業(yè)額有超過 $1,500。在這個情況下,我們不能使用 WHERE 的指令。那要怎么辦呢?很幸運地,SQL 有提供一個 HAVING 的指令,而我們就可以用這個指令來達(dá)到這個目標(biāo)。 HAVING 子句通常是在一個 SQL 句子的最后。一個含有 HAVING 子句的 SQL 并不一定要包含 GROUP BY 子句。HAVING 的語法如下:
SELECT "欄位1", SUM("欄位2")
FROM "表格名"
GROUP BY "欄位1"
HAVING (函數(shù)條件);
| student | class |
|---|---|
| A | Math |
| B | English |
| C | Math |
| D | Biology |
| E | Math |
| F | Computer |
| G | Math |
| H | Math |
| I | Math |
對于上表courses 中找到所有有至少5個不同學(xué)生選擇了的課程
結(jié)果是:
| class |
|---|
| Math |
#這里可能會存在同樣的學(xué)生選了同樣的課被多次列舉,所以后面用到了distinct student
select
class
from
courses
group by class
having count(distinct student)>=5
1.LeetCode627
主要學(xué)習(xí)update語句以及數(shù)據(jù)格式轉(zhuǎn)化后的異或操作,ASCII,CHAR格式轉(zhuǎn)化的用法
| id | name | sex | salary |
|---|---|---|---|
| 1 | A | m | 2500 |
| 2 | B | f | 1500 |
| 3 | C | m | 5500 |
| 4 | D | f | 500 |
將表salary中所有sex的m轉(zhuǎn)化成f,f轉(zhuǎn)化成m
update salary
set sex = CHAR(ASCII('m')^ASCII('f')^ASCII(sex))