最近碰到一些小問題, 本來都是使用PHP來幫忙解決,
但是今天利用了SQL一次解決, 讓我覺得有夠開心的想來分享一下。
描述問題
現在有三個table, 因為原始設計網站的架構不太彈性, 所使用的class寫法也很虛, 害我等自己echo語法出來慢慢比對,
啊, 一不小心就開始抱怨了起來。
三個table分別是: m_info, m_detail, 和 m_position。
當然, 這是簡化過問題且虛擬的表格。
m_info
|
m_detail
|
m_position
|
其中mid為每個table聯繫用的key, 是auto_increasement的一個欄位。
想顯示出的結果為:
mid | name | phone | position |
1 | 彭小胖 | 22222222 | 總裁 |
2 | 王大明 | 12345678 | 總裁 |
3 | 李小帥 | 11111111 | 總裁 |
4 | 林冷生 | 33333333 | NULL |
5 | 錢快來 | 44444444 | NULL |
意義是:彭小胖為現任總裁, 因此先取出來擺放在第一位, 接著依照擔任總裁的日期擺放, 最後才擺入沒有擔任過職位的人。
那麼SQL的語法要怎麼寫呢?
SELECT mid, position, phone, CASE WHEN (m_date>='2009-01-01' AND position='會長') THEN 1 ELSE 2 END as m_first, CASE WHEN position is null THEN 2 ELSE 1 END as m_sort FROM m_info JOIN m_detail ON m_detail.mid=m_info.mid LEFT JOIN m_position ON m_position.mid=m_info.mid WHERE GROUP BY mid ORDER BY m_first ASC, m_sort ASC, m_date ASC
紅色字體中的CASE WHEN是這篇文章的重點, 因為我們用條件將總裁職位中欄位date最新的人給取出來(這個條件可以搭配PHP或是ASP.NET等來改變),
先給它一個值, 然後其餘的人給予不同的值, 接著把這個條件alias給m_first這個別名, 最後再使用ORDER BY先進行這個別名的排序。
第二個CASE WHEN目的則是在區分有擔任過職位的人和沒擔任過職位的人, 原理同上方敘述一樣。
GROUP BY則是因為有可能很多人會擔任很多職位, 或是不同時期擔任別的職位之類的, 但是我目前的需求是相同的人只要出現一筆,
於是我利用GROUP BY mid來將相同的人合在一起。
後註:這篇文章讓我寫了三次, 三個不一樣的版本, 而且一直很難上傳...我真的很想對痞克邦罵聲...!
留言列表