0718 SQL SELECT

onnbi·2022년 7월 27일
0

sql-tutorial

목록 보기
4/6
post-thumbnail

SELECT

SQL에서 CRUD를 담당하는 DML(SELECT, INSERT, UPDATE, DELETE) 중에서 데이터를 추출하기 위해 사용되는 언어를 DQL(SELECT)라고 한다

데이터를 조회한 결과로 0개 이상의 행을 포함하는 RESULT SET을 갖는다

SELECT 컬럼명 (,컬럼명...) FROM 테이블명 WHERE 조건

  1. FROM 테이블로부터 2. WHERE조건에 맞는 3. SELECT컬럼을 보여준다

* : 모든 컬럼을 다 보고 싶을 때

SELECT 사용법

테이블에 없는 데이터도 산술식을 통해 가져올 수 있다

-- 주석
-- 직원 테이블에서,
-- 이름, 이메일, 전화번호, 월급을 보여줘
-- 월급이 250만원 이상인 직원
SELECT EMP_NAME, EMAIL, PHONE, SALARY FROM EMPLOYEE WHERE SALARY>=2500000;

SELECT문을 작성할 때 컬럼에 별칭을 줄 수 있다

SELECT EMP_NAME AS "이름", SALARY "월급", SALARY*12 연봉,
--1. AS "별칭" 2. "별칭"		
(SALARY+(SALARY*BONUS))*12"연봉(보너스포함)" FROM EMPLOYEE;
--3. 별칭만 

지정한 문자열을 리터럴로 가진 단위 컬럼을 만들 수 있다

SELECT EMP_NAME, SALARY,'원' 단위 FROM EMPLOYEE;
-- '원'=값자체 리터럴
-- 월급에 단위를 붙여주기 위한 리터럴

DISTINCT

SELECT DISTINCT JOB_CODE FROM EMPLOYEE;
-- 컬럼에 포한됨 중복값을 한번씩만 표시

연결연산자

|| : 여러컬럼을 하나의 컬럼인 것처럼 연결 || 컬럼과 리터럴을 연결

SELECT EMP_NAME, SALARY+'원' FROM EMPLOYEE;
-- JAVA처럼 +연산자로 붙여줄 수 없다
SELECT EMP_NAME, SALARY||'원' FROM EMPLOYEE;
-- 8000000원
SELECT EMP_ID||EMP_NAME FROM EMPLOYEE;
-- 컬럼이 하나의 컬럼처럼 붙어서 출력

논리연산자

AND : 여러조건이 동시에 TRUE일 경우 TRUE

OR : 여러조건 중 하나라도 TRUE일 경우 TRUE

NOT : 조건에 대한 반대로 반환 (NULL제외)

비교연산자

TRUE / FALSE / NULL 결과 반환

SELECT 비교연산자
=
>, <
>=, =<
<>, !=, ^=같지 않다
BERWEEN A AND B특정범위에 포함되는지 비교
LIKE, NOT LIKE문자 패턴 비교
IS NULL, IS NOT NULLNULL 여부 비교
IN, NOT IN비교 값 목록에 포함/미포함

LIKE / NOT LIKE

비교하려는 값이 특정 패턴을 만족시키면 TRUE 리턴

※ 와일드카드

% : 글자수 제한없이 퍼센트 하나로 대체

_ : 한 글자 대체 (글자수만큼 _)

ESCAPE : 와일드 카드를 예외처리 해준다 (JAVA의 '\' )

WHERE EMP_NAME LIKE '전__';
WHERE EMP_NAME LIKE '전%';
-- 성이 '전'인 사람 조회

WHERE EMAIL LIKE '___#_%'ESCAPE'#';
-- 이메일 4번째 글자가 _인 사람 조회
-- '#'뒤에 글자는 와일드카드가 아니라는 의미

IS NULL / IS NOT NULL

-- 비어있는지, 아닌지
SELECT EMP_NAME, BONUS FROM EMPLOYEE WHERE BONUS IS NULL;

IN / NOT IN

-- 이름, 부서코드  부서코드가 D9 또는 D6 또는 D8
SELECT EMP_NAME, DEPT_CODE FROM EMPLOYEE
WHERE DEPT_CODE NOT IN ('D9','D6','D8');

※ 연산순서

산술 > 연결 > 비교 > IS/LIKE > BETWEEN >NOT > AND > OR

JOIN

sql_join

  • INNER JOIN : NULL값은 포함하지 않고 출력
  • OUTER JOIN
    • LEFT JOIN : A의 NULL값은 포함하여 출력
    • RIGHT JOIN : B의 NULL값은 포함하여 출력
    • FULL JOIN : A와 B의 NULL값을 모두 포함하여 출력
  • CROSS JOIN
SELECT EMP_NAME, DEPT_CODE, DEPT_TITLE
FROM EMPLOYEE CROSS JOIN DEPARTMENT;
-- 모든 DEPT_TITLE과 한 번씩 매치
  • SELF JOIN : A table에 A table을 조인
SELECT E1.EMP_NAME "사원명", DEPT_TITLE "부서명", E2.EMP_NAME "동료이름"
FROM EMPLOYEE E1
JOIN DEPARTMENT ON (DEPT_ID = DEPT_CODE)
JOIN EMPLOYEE E2 ON (E1.DEPT_CODE = E2.DEPT_CODE)
WHERE E1.EMP_NAME NOT IN E2.EMP_NAME
ORDER BY 1;
  • 다중조인 : 1개의 SELECT문 안에서 여러 번 JOIN
-- 다중조인 + SELF JOIN
SELECT E1.EMP_NAME "사원명", DEPT_TITLE "부서명", E2.EMP_NAME "동료이름"
FROM EMPLOYEE E1
JOIN DEPARTMENT ON (DEPT_CODE = DEPT_ID)
JOIN EMPLOYEE E2 ON (E1.DEPT_CODE = E2.DEPT_CODE)
WHERE E1.EMP_NAME != E2.EMP_NAME
ORDER BY 1;

SET OPERATOR

집합연산자

여러 개의 테이블에서 JOIN을 사용하지 않고 연관된 데이터를 조회하는 방법

여러 개의 조회결과를 결합하는 방식

JOIN은 컬럼을 추가하여 추가 데이터를 표현, 집합연산자는 ROW를 추가하여 추가 데이터를 표현

<성립 조건>

  1. SELECT 절의 컬럼 수가 동일해야 한다
  2. SELECT 절의 동일 위치에 존재하는 컬럼 데이터가 상호 호환 가능해야 한다

합집합

  • UNION
    • 중복되는 데이터 제거
    • 첫 번째 컬럼 기준 오름차순 정렬
  • UNION ALL
    • 중복 데이터 제거 X
    • 정렬 X

교집합

  • INTERSECT : 두 SELECT문에서 공통된 부분만 추출

차집합

  • MINUS : 첫번째 결과에서 두 번째 조회문과 겹치는 부분 제거

SUBQUERY

SELECT문 안에 또다른 SELECT문을 포함

서브쿼리는 메인 쿼리 실행 전 한 번만 실행

<서브쿼리 조건>

  1. 서브 쿼리는 반드시 소괄호로 묶어야 한다
  2. 서브쿼리와 비교할 항목은 서브쿼리의 SELECT한 항목과 자료형과 개수가 동일해야 한다

<서브쿼리 유형>

  1. 단일행 서브쿼리

    ex ) 전직원의 평균급여보다 많은 급여를 받는 직원의 사번, 이름, 급여 조회

    • 전직원의 평균급여를 구한다 (단일값)
    • 평균급여를 이용한 쿼리문을 작성한다
  2. 다중행 서브쿼리

    ex ) 부서별 최고 급여를 받는 직원의 이름, 직급, 부서, 급여 조회

    • 여러 값을 한 번에 조회할 수 있는 IN연산자를 통해 비교한다
    SELECT EMP_NAME, DEPT_CODE, SALARY
    FROM EMPLOYEE
    WHERE SALARY IN (SELECT MAX(SALARY) FROM EMPLOYEE GROUP BY DEPT_CODE);
    • 사용할 수 있는 연산자 : IN / NOT IN / ANY / ALL
  3. 다중열 서브쿼리

  4. 다중행 다중열 서브쿼리

  5. 상관 서브쿼리 (상호연관 서브쿼리)

    • 독립적이지 않고 상호연관
    • 메인쿼리 값을 서브쿼리에 주고, 서브쿼리를 수행한 후 다시 메인쿼리 수행
  6. 스칼라 서브쿼리

    • 상호연관 서브커리이면서 결과값이 1개인 서브쿼리 (SELECT절 사용 스칼라)

    EX ) 모든 사원의 사번, 이름, 관리자 번호, 관리자이름 조회

    SELECT EMP_ID, EMP_NAME, MANAGER_ID,
    (SELECT E2.EMP_NAME FROM EMPLOYEE E2 WHERE E2.EMP_ID = E1.MANAGER_ID) AS 관리자명
    FROM EMPLOYEE E1;
    • 하나의 컬럼으로 사용할 수 있다
    • JOIN을 사용하지 않고도 테이블을 합칠 수 있다

인라인 뷰

뷰 : 가상의 테이블
인라인 뷰 : FROM에서 사용하는 서브쿼리

SELECT *	-- 가상의 테이블에 포함한 컬럼만 조회 가능
FROM (SELECT EMP_NAME, DEPT_CODE, JOB_CODE, SALARY FROM EMPLOYEE);
  • TOP-N 분석
SELECT ROWNUM, EMP_NAME, DEPT_CODE, SALARY
FROM (SELECT EMP_NAME, DEPT_CODE, SALARY
      FROM EMPLOYEE ORDER BY SALARY DESC) 
WHERE ROWNUM<6;
-- ROWNUM : 컬럼 앞에 붙는 번호를 컬럼처럼 사용하도록 한다
----------------------------------------------------------------
SELECT ROWNUM, EMP_NAME, DEPT_CODE, SALARY
FROM EMPLOYEE ORDER BY SALARY DESC;
-- 그냥 ROWNUM할 경우 ORDER BY가 가장 늦게 동작하기 때문에
-- SALARY기준이 틀어진다
-- 먼저 SALARY정렬 기준으로 내림차순 한 테이블을 만들어 둔 다음
-- 해당 테이블에 ROWNUM을 붙여준다
----------------------------------------------------------------
SELECT EMP_NAME, SALARY,
RANK() OVER(ORDER BY SALARY DESC)
FROM EMPLOYEE;
SELECT EMP_NAME, SALARY,
DENSE_RANK() OVER(ORDER BY SALARY DESC)
FROM EMPLOYEE;
SELECT EMP_NAME, SALARY,
ROW_NUMBER() OVER(ORDER BY SALARY DESC)
FROM EMPLOYEE;

ROWNUM 대체 함수

RANK() OVER(ORDER BY 컬럼 DESC) :
같은 순위가 2일 때 다음 순위 +1

DENSE_RANK() OVER(ORDER BY 컬럼 DESC) :
같은 순위가 2일 때 다음 순위 바로 연결

ROW_NUMBER() OVER(ORDER BY 컬럼 DESC)
같은 순위 무시하고 연결

profile
aelatte coding journal

0개의 댓글