SQL 查詢實例

字符串處理

數(shù)據(jù)準備:

create table n10(
  pos int4
);
insert into n10 (pos) values (1);
insert into n10 (pos) values (2);
-- ... 1 到 10
insert into n10 (pos) values (10);
--
create table table3(
  name text,
  address text
);
insert into table3 (line) values ('aladdin', 'china');
  • 串聯(lián)字符串
-- Postgres / Oracle
select name || ' live in ' || address as msg from table3; -- aladdin live in china
-- MySQL / Postgres
select concat(name, ' live in ', address) as msg from table3; -- aladdin live in china
select concat_ws('_', name, address) from table8; -- aladdin_china
  • 查找匹配項
-- PostgreSQL / MySQL
select * from emp where emp_sal in (13000, 30000); -- 使用 in
-- 使用 like
select * from emp where emp_name like 'ala%'; -- 匹配單個字符使用 '_'
  • 遍歷字符串
-- Postgres
select
       substring(t3.name, iter.pos, 1) as c
from
     table3 t3, n10 iter
where
      iter.pos <= length(t3.name);
-- a
-- l
-- a
-- d
-- d
-- i
-- n
  • 統(tǒng)計字符出現(xiàn)的次數(shù)
-- Postgres
select
       (length(name) - length(replace(name, 'a', ''))) as num
       -- 統(tǒng)計字符 a 出現(xiàn)的次數(shù)
from table3; -- 2
  • 刪除不想要的字符
-- Postgres
select
       replace(translate(line, 'AEIOUaeiou', 'aaaaaaaaaa'), 'a', '')
       -- 將元音字符刪除
from table3;
  • 分離字符串和數(shù)字
-- 準備工作
create table table1(
  line text
);
insert into table1 (line) values ('Jim1006');
-- Postgres
select
       replace(translate(line, '0123456789', '0000000000'), '0', '') as ename,
       cast(replace(translate(lower(line), 'asdfghjklzxcvbnmqwertyuiop', repeat('z', 26)), 'z', '') as integer) as year
from table1 t1;
  • 按字符串中的數(shù)字排序
-- Postgres
select line
from table1
order by cast(replace(translate(lower(line), 'asdfghjklzxcvbnmqwertyuiop', repeat('z', 26)), 'z', '') as integer);
  • 解析IP地址
create table table2(
  ip text
);
insert into table2 (ip) values ('144.132.11.3');
-- MySQL
select
       substring_index(substring_index(ip, '.', 1), '.', -1) as a,
       substring_index(substring_index(ip, '.', 2), '.', -1) as b,
       substring_index(substring_index(ip, '.', 3), '.', -1) as c,
       substring_index(substring_index(ip, '.', 4), '.', -1) as d
from table2;
-- PostgreSQL
select
       split_part(ip, '.', 1) as a,
       split_part(ip, '.', 2) as b,
       split_part(ip, '.', 3) as c,
       split_part(ip, '.', 4) as d
from table2;

數(shù)值處理

數(shù)據(jù)準備:

create table table3(
  id int4,
  score double precision
);
insert into table3 (id, score) values (1001, 97);
insert into table3 (id, score) values (1001, 95);
insert into table3 (id, score) values (1001, 98);
insert into table3 (id, score) values (1002, 93);
insert into table3 (id, score) values (1002, 99);
insert into table3 (id, score) values (1003, 94);
insert into table3 (id, score) values (1003, 99);
  • 計算均值
select avg(score) from table3;
-- 分組求均值
select id, round(avg(score)::numeric, 2) from table3 group by id;
select id, round(avg(coalesce(t3.score, 0))::numeric, 2) from table3 t3 group by id;
  • 去掉極值求均值
select
       avg(score)
from
     table3
where
      score not in (
                    (select max(score) from table3),
                    (select min(score) from table3)
                   );
  • 最大值與最小值
select min(score) as min, max(score) as max from table3;
-- 分組求最大值與最小值
select id, min(score) as min, max(score) as max from table3 group by id;
select id, min(coalesce(score, 0)) as min, max(coalesce(score, 0)) as max from table3 group by id;
  • 求和
select sum(score) as sum from table3;
-- 分組求和
select id, sum(score) as sum from table3 group by id;
select id, sum(coalesce(score, 0)) from table3 group by id;
  • 計算行數(shù)
-- count(*) 統(tǒng)計行數(shù)忿等,無論非 null 否
select count(*) as count from table3;
-- 計算某列值個數(shù)
select count(score) as count -- 如果 score 為 null 則不計數(shù)
from table3;
-- 分組求行數(shù)
select id, count(*) as count from table3 group by id;
  • 求眾數(shù)
select score
from
     (
       select
              score, (dense_rank() over (order by e.count desc)) as rnk
       from
            (
              select score, count(score) as count
              from table3
              group by score
            ) as e
     ) as t
where t.rnk = 1;
  • 計算百分比
-- 計算 id 為 1001 學生分數(shù)占全部分數(shù)的百分比
select (sum(case when id = 1001 then score end) / sum(score)) * 100 as pct from table3;

日期處理

  • 提取年月日
-- Postgres
select extract(year from now()) as year;
-- mon: 月
-- day: 日
-- week: 一年中第幾周
-- doy: 一年中第幾天

對 NULL 值處理

  • 查找 NULL 值
-- PostgreSQL / MySQL
select * from emp where emp_name is null;
  • 將 NULL 值轉換為實際值
-- PostgreSQL / MySQL
select coalesce(emp_name, 'Secret Superstar') as name from emp;
  • 比較中有 NULL 值
-- 數(shù)據(jù)準備
create table table2(
  name text,
  sal double precision
);
create table table3(
  name text,
  sal double precision
);
insert into table2 (name, sal) values ('aladdin', 12000), ('bilib', null);
insert into table3 (name, sal) values ('chrome', 3000);
-- 使用 coalesce 函數(shù)進行 null 值的轉換
select * from table2 t2
where coalesce(t2.sal, 0) > (select t3.sal from table3 t3 where t3.name = 'chrome');

CASE...WHEN

  • PostgerSQL / MySQL /Oracle
select
     emp_name,
     emp_sal,
     case
       when emp_sal < 10000.0 then 'low'
       when emp_sal >= 10000.0 and emp_sal < 20000.0 then 'mid'
       when emp_sal >= 20000.0 and emp_sal < 50000.0 then 'high'
       else 'very high'
     end as "status"
from emp;

返回指定行數(shù)

  • PostgreSQL / MySQL
-- 返回指定行數(shù)菌瘫,PostgreSQL 和 MySQL 一樣
select * from emp order by emp_sal limit 3;
-- 隨機返回 N 行,Postgre 實現(xiàn)
select * from emp order by random() limit 3;
-- 隨機返回 N 行,MySQL 實現(xiàn)
select * from emp order by rand() limit 3;
  • Oracle
select * from emp where rownum <= 3;

排序

  • 基本排序
-- PostgreSQL / MySQL
-- 單字段
select * from emp order by emp_sal desc; -- 將序忿危,默認升序 / asc
-- 多字段
select * from emp order by emp_sal desc, emp_name;
-- 子字段
select * from emp order by substr(emp_name, length(emp_name) - 2);
  • 對字段中的數(shù)字 / 字母排序
-- 數(shù)據(jù)處理
create table public.table2(
msg text
);
insert into public.table2 values ('aladdin 800'), ('bilib 300'), ('chrom 600');

-- 下面連個方法對 MySQL 不適用
-- 對字段中的數(shù)字排序
select
     *
from
   public.table2
order by
       replace(msg, replace(translate(msg, '0123456789', '#########'), '#', ''), '');
-- 對字段中的字母進行排序
select
     *
from public.table2
order by
       replace(translate(msg, '0123456789', '#########'), '#', '');
  • 對 NULL 進行更高級的排序
-- 數(shù)據(jù)準備
create table table4(
name text,
sal double precision
);
insert into
public.table4(name, sal)
values 
       ('alad', 0),
       ('bilib', 500),
       ('chrome', 1000),
       ('dell', null),
       ('echo', null);


-- 最基本的排序
select * from public.table4 order by sal desc; -- 這樣 null 值就會到最上面
-- 讓 null 值下來
with temp as(
select name,
       sal,
       case
         when sal is null
           then 0 else 1
         end as is_null
from public.table4
)
select name, sal from temp order by is_null desc, sal desc; -- 其它解決方案類似
  • 根據(jù)條件排序
select * from table4
order by
       case 
         when name = 'alad'
           then sal
         else name
       end desc;

集合操作

  • 合并
    UNION 會去重復項,UNION ALL 不會,如果不是特殊要求,一般都使用 UNION ALL若厚,UNION 相當于在 UNION ALL 的基礎上做一次 distinct 操作:
select name, sal from table5
union all
select name, sal from public.table6;
  • 交集與差集
-- 數(shù)據(jù)準備
create table public.table1(
name text,
hobby text
);
insert into
public.table1 (name, hobby)
values
       ('aladdin', 'Ping pong'),
       ('aladdin', 'Computer games'),
       ('bilil', 'Basketball'),
       ('bilib', 'Computer games');

-- Postgres
-- intersect 求交集
select
     hobby
from
   table1
where
    name = 'aladdin'
intersect
select
     hobby
from
   table1
where name = 'bilib'; -- Computer games

-- 使用基礎語句實現(xiàn)
select
     t1.hobby
from table1 t1
inner join table1 t2 
  on
    t1.name = 'aladdin' and
    t2.name = 'bilib' and
    t1.hobby = t2.hobby;

-- (A - B) 求差集,Oracle 使用 minus 關鍵字實現(xiàn)
select
     hobby
from
   table1
where
    name = 'aladdin'
except
select
     hobby
from table1
where
    name = 'bilib'; -- Ping pong

-- 使用子查詢實現(xiàn)
select
     t1.hobby
from
   table1 t1
where
    t1.name = 'aladdin' and t1.hobby not in (select t2.hobby from table1 t2 where t2.name = 'bilib');
最后編輯于
?著作權歸作者所有,轉載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末蜒什,一起剝皮案震驚了整個濱河市测秸,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖乞封,帶你破解...
    沈念sama閱讀 211,743評論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異岗憋,居然都是意外死亡肃晚,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,296評論 3 385
  • 文/潘曉璐 我一進店門仔戈,熙熙樓的掌柜王于貴愁眉苦臉地迎上來关串,“玉大人,你說我怎么就攤上這事监徘〗蓿” “怎么了?”我有些...
    開封第一講書人閱讀 157,285評論 0 348
  • 文/不壞的土叔 我叫張陵凰盔,是天一觀的道長墓卦。 經(jīng)常有香客問我,道長户敬,這世上最難降的妖魔是什么落剪? 我笑而不...
    開封第一講書人閱讀 56,485評論 1 283
  • 正文 為了忘掉前任,我火速辦了婚禮尿庐,結果婚禮上忠怖,老公的妹妹穿的比我還像新娘。我一直安慰自己抄瑟,他們只是感情好凡泣,可當我...
    茶點故事閱讀 65,581評論 6 386
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著皮假,像睡著了一般鞋拟。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上惹资,一...
    開封第一講書人閱讀 49,821評論 1 290
  • 那天严卖,我揣著相機與錄音,去河邊找鬼布轿。 笑死哮笆,一個胖子當著我的面吹牛,可吹牛的內(nèi)容都是我干的汰扭。 我是一名探鬼主播稠肘,決...
    沈念sama閱讀 38,960評論 3 408
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼萝毛!你這毒婦竟也來了项阴?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 37,719評論 0 266
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎环揽,沒想到半個月后略荡,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 44,186評論 1 303
  • 正文 獨居荒郊野嶺守林人離奇死亡歉胶,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,516評論 2 327
  • 正文 我和宋清朗相戀三年汛兜,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片通今。...
    茶點故事閱讀 38,650評論 1 340
  • 序言:一個原本活蹦亂跳的男人離奇死亡粥谬,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出辫塌,到底是詐尸還是另有隱情漏策,我是刑警寧澤,帶...
    沈念sama閱讀 34,329評論 4 330
  • 正文 年R本政府宣布臼氨,位于F島的核電站掺喻,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏储矩。R本人自食惡果不足惜巢寡,卻給世界環(huán)境...
    茶點故事閱讀 39,936評論 3 313
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望椰苟。 院中可真熱鬧抑月,春花似錦、人聲如沸舆蝴。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,757評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽洁仗。三九已至层皱,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間赠潦,已是汗流浹背叫胖。 一陣腳步聲響...
    開封第一講書人閱讀 31,991評論 1 266
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留她奥,地道東北人瓮增。 一個月前我還...
    沈念sama閱讀 46,370評論 2 360
  • 正文 我出身青樓,卻偏偏與公主長得像哩俭,于是被迫代替她去往敵國和親绷跑。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 43,527評論 2 349

推薦閱讀更多精彩內(nèi)容

  • ORACLE自學教程 --create tabletestone ( id number, --序號usernam...
    落葉寂聊閱讀 1,072評論 0 0
  • Oracle SQL基本操作 Oracle數(shù)據(jù)庫基本操作 1.概述 Oracle數(shù)據(jù)庫客戶端一般需要安裝在服務器上...
    橫豎撇捺啊閱讀 529評論 0 1
  • 1.簡介 數(shù)據(jù)存儲有哪些方式凡资?電子表格砸捏,紙質(zhì)文件,數(shù)據(jù)庫。 那么究竟什么是關系型數(shù)據(jù)庫垦藏? 目前對數(shù)據(jù)庫的分類主要是...
    喬震閱讀 1,710評論 0 2
  • 1. select * from emp; 2. select empno, ename, job from em...
    海納百川_4d26閱讀 1,896評論 0 4
  • 周末的上午用來碼字梆暖,那就寫一點自己昨天想到的內(nèi)容,再不寫可能就忘記了掂骏。 第一轰驳,跑道思維,就像好像說沈南鵬的紅杉資本...
    yichen大刀閱讀 155評論 0 0