
SQL์ ์์ฑํ๋ค ๋ณด๋ฉด WHERE ์ ์ ์กฐ๊ฑด์ ์ฐ๋ฌ์ ์ฐ๊ธฐ ์ ๋งคํ๊ฑฐ๋,
FROM ์ ์ ๋ค์ด๊ฐ ํ
์ด๋ธ์ด ๋จผ์ ์ด๋ ์ ๋ ์ ์ ๋ ์ํ์ฌ์ผ ํ๋ ๊ฒฝ์ฐ๊ฐ ์๊ธด๋ค.
์ด๋ด ๋ ์๋ธ์ฟผ๋ฆฌ(Subquery) ๋ฅผ ์ฌ์ฉํ๋ค.
์๋ธ์ฟผ๋ฆฌ๋ ์ฟผ๋ฆฌ๋ฌธ ์์ ๋ ๋ค๋ฅธ ์ฟผ๋ฆฌ๋ฌธ์ ์ค์ฒฉํด์ ์ฌ์ฉํ๋ ๋ฐฉ์์ผ๋ก,
ํฌ๊ฒ ๋ ๊ฐ์ง ์ฉ๋๋ก ํ์ฉ๋๋ค.
WHERE ์ ์์ ํน์ ์กฐ๊ฑด ๊ฐ์ ๋์ ์ผ๋ก ๊ตฌํ ๋FROM ์ ์์ 1์ฐจ ์ ์ ๋ ๊ฐ์์ ํ
์ด๋ธ๋ก ์ฌ์ฉํ ๋์ด๋ฒ ์ค์ต์์๋ ์ ์ , ๊ฒ์๊ธ, ๋๊ธ ์ธ ๊ฐ์ ํ ์ด๋ธ์ ์ฌ์ฉํ๋ค.
-- ์ ์ ํ
์ด๋ธ
CREATE SEQUENCE SEQ_USER;
CREATE TABLE TBL_USER (
ID NUMBER CONSTRAINT PK_USER PRIMARY KEY,
USER_EMAIL VARCHAR2(255) NOT NULL UNIQUE,
USER_PASSWORD VARCHAR2(255),
USER_ADDRESS VARCHAR2(255),
USER_BIRTH DATE
);
-- ๊ฒ์๊ธ ํ
์ด๋ธ
CREATE SEQUENCE SEQ_POST;
CREATE TABLE TBL_POST (
ID NUMBER CONSTRAINT PK_POST PRIMARY KEY,
POST_TITLE VARCHAR2(255) NOT NULL,
POST_CONTENT VARCHAR2(255) NOT NULL,
POST_CREATE_AT TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
USER_ID NUMBER,
CONSTRAINT FK_POST_USER FOREIGN KEY (USER_ID) REFERENCES TBL_USER(ID)
);
-- ๋๊ธ ํ
์ด๋ธ
CREATE SEQUENCE SEQ_REPLY;
CREATE TABLE TBL_REPLY (
ID NUMBER CONSTRAINT PK_REPLY PRIMARY KEY,
REPLY_CONTENT VARCHAR2(255) NOT NULL,
USER_ID NUMBER,
POST_ID NUMBER,
CONSTRAINT FK_REPLY_USER FOREIGN KEY (USER_ID) REFERENCES TBL_USER(ID),
CONSTRAINT FK_REPLY_POST FOREIGN KEY (POST_ID) REFERENCES TBL_POST(ID)
);
ํ ์ด๋ธ์ ์ธ๋ํค(FK)๋ก ์๋ก ์ฐ๊ฒฐ๋์ด ์๋ค.
์ด ๊ด๊ณ๋ฅผ ๋ฐํ์ผ๋ก ์๋ธ์ฟผ๋ฆฌ๋ฅผ ํ์ฉํ ๋ค์ํ ์กฐํ๊ฐ ๊ฐ๋ฅํ๋ค.
์๋ ์์๋ TBL_USER์์ ์ฃผ์๊ฐ '๋ก์'์ ํฌํจํ๋ ์ ์ ๊ฐ ์์ฑํ ๊ฒ์๊ธ์ ์กฐํํ๋ ์ฟผ๋ฆฌ๋ค.
SELECT *
FROM TBL_POST
WHERE USER_ID IN (
SELECT ID
FROM TBL_USER
WHERE USER_ADDRESS LIKE '%๋ก์%'
);
USER_ID ๋ชฉ๋ก์ ๋ฐํํ๋ค.IN ์กฐ๊ฑด์ผ๋ก ํ์ฉํด ๊ฒ์๊ธ์ ํํฐ๋งํ๋ค.์๋ธ์ฟผ๋ฆฌ์ ํต์ฌ์ ํ ๋ฒ์ ์์ฑํ๋ ค ํ์ง ์๋ ๊ฒ์ด๋ค.
๋จ๊ณ๋ณ๋ก ์ฟผ๋ฆฌ๋ฅผ ์ชผ๊ฐ์ ์๊ฐํ๊ณ , ํ๋์ฉ ๊ฒ์ฆํ๋ฉด์ ์์ฑํด ๋๊ฐ์ผ ํ๋ค.
SELECT * FROM TBL_REPLY;
SELECT POST_ID, COUNT(POST_ID) AS "REPLY_COUNT"
FROM TBL_REPLY
GROUP BY POST_ID;
SELECT MAX(COUNT(POST_ID))
FROM TBL_REPLY
GROUP BY POST_ID;
SELECT POST_ID
FROM TBL_REPLY
GROUP BY POST_ID
HAVING COUNT(POST_ID) = (
SELECT MAX(COUNT(POST_ID))
FROM TBL_REPLY
GROUP BY POST_ID
);
SELECT *
FROM TBL_POST
WHERE ID IN (
SELECT POST_ID FROM TBL_REPLY
GROUP BY POST_ID
HAVING COUNT(POST_ID) = (
SELECT MAX(COUNT(POST_ID))
FROM TBL_REPLY
GROUP BY POST_ID
)
);
SELECT USER_ID
FROM TBL_POST
WHERE ID IN (
SELECT POST_ID FROM TBL_REPLY
GROUP BY POST_ID
HAVING COUNT(POST_ID) = (
SELECT MAX(COUNT(POST_ID))
FROM TBL_REPLY
GROUP BY POST_ID
)
);
SELECT *
FROM TBL_USER
WHERE ID IN (
SELECT USER_ID FROM TBL_POST
WHERE ID IN (
SELECT POST_ID FROM TBL_REPLY
GROUP BY POST_ID
HAVING COUNT(POST_ID) = (
SELECT MAX(COUNT(POST_ID))
FROM TBL_REPLY
GROUP BY POST_ID
)
)
);
โ ๏ธ ์๋ธ์ฟผ๋ฆฌ๊ฐ 3๋จ๊ณ๋ก ์ค์ฒฉ๋๋ฉด์ ๊ฐ๋ ์ฑ์ด ๋จ์ด์ง๋ค.
์ด ๋ฌธ์ ๋ ์ถํ JOIN์ ํ์ตํ๋ฉด ํจ์ฌ ๊ฐ๊ฒฐํ๊ฒ ์์ฑํ ์ ์๋ค.
ํ์ง๋ง ์๋ธ์ฟผ๋ฆฌ๋ง์ผ๋ก๋ ์ถฉ๋ถํ ์ํ๋ ๊ฒฐ๊ณผ๋ฅผ ์ป์ ์ ์๋ค๋ ์ ์ด ํต์ฌ์ด๋ค.
์๋ธ์ฟผ๋ฆฌ ์ธ์๋ CASE WHEN ๊ตฌ๋ฌธ์ ์ฌ์ฉํ๋ฉด
ํน์ ์กฐ๊ฑด์ ๋ฐ๋ผ ์ถ๋ ฅ ๊ฐ์ ๋ค๋ฅธ ๊ฐ์ผ๋ก ๋์นํ ์ ์๋ค.
SELECT
USER_EMAIL,
CASE
WHEN USER_BIRTH >= TO_DATE('2000', 'YYYY') THEN '2000๋
๋ ์'
WHEN USER_BIRTH < TO_DATE('2000', 'YYYY') THEN '1990๋
๋ ์'
END AS "ํ์ด๋ ๋
๋"
FROM TBL_USER;
CASE WHEN ... THEN ... END ๊ตฌ์กฐ๋ก ์กฐ๊ฑด๋ณ ๋ถ๊ธฐ ์ถ๋ ฅ์ด ๊ฐ๋ฅํ๋ค.AS)์ ๋ถ์ฌ ์ปฌ๋ผ ์ด๋ฆ์ ๋ณด๊ธฐ ์ข๊ฒ ์ง์ ํ ์ ์๋ค.| ๊ฐ๋ | ์ค๋ช |
|---|---|
| ์๋ธ์ฟผ๋ฆฌ | ์ฟผ๋ฆฌ ์์ ๋ ๋ค๋ฅธ ์ฟผ๋ฆฌ๋ฅผ ์ค์ฒฉํ๋ ๋ฐฉ์ |
WHERE IN (์๋ธ์ฟผ๋ฆฌ) | ์๋ธ์ฟผ๋ฆฌ ๊ฒฐ๊ณผ๋ฅผ ์กฐ๊ฑด ๊ฐ์ผ๋ก ํ์ฉ |
HAVING + ์๋ธ์ฟผ๋ฆฌ | ์ง๊ณ ๊ฒฐ๊ณผ๋ฅผ ๊ธฐ์ค์ผ๋ก ํํฐ๋ง |
CASE WHEN | ์กฐ๊ฑด์ ๋ฐ๋ผ ์ถ๋ ฅ ๊ฐ์ ๋ณํ |
| ๋จ๊ณ๋ณ ์ ๊ทผ | ์๋ธ์ฟผ๋ฆฌ๋ ํ ๋ฒ์ ์์ฑํ๋ ค ํ์ง ๋ง๊ณ ๋จ๊ณ์ ์ผ๋ก ์์ฑ |
์๋ธ์ฟผ๋ฆฌ์ ํต์ฌ์ "๋จ๊ณ๋ณ๋ก ์๊ฐํ๊ธฐ" ๋ค.
๋ณต์กํ ๋ฌธ์ ์ผ์๋ก ์์ ์ฟผ๋ฆฌ๋ถํฐ ๊ฒ์ฆํ๊ณ ์์ ์ฌ๋ ค์ผ ํ๋ค.
JOIN์ ๋ฐฐ์ฐ๋ฉด ๋ ๊น๋ํ๊ฒ ํํํ ์ ์์ง๋ง,
์๋ธ์ฟผ๋ฆฌ๋ง์ผ๋ก๋ ์ถฉ๋ถํ ๊ฐ๋ ฅํ ์ฟผ๋ฆฌ ์์ฑ์ด ๊ฐ๋ฅํ๋ค. ๐ช