본문 바로가기

Database

DATABASE 7장

NULL을 포함한 비교와 3값 논리에 대한 비교 NULL : 모르는 값, 가용되지 않은 값 TRUE,FALSE와 UNKNOWN 의 AND연산값 주목
 SQL에서 NULL값을 찾을때나 그 반대일때 = NULL 이 아니라 IS [NOT] NULL로 WHERE에 명세
1,2,3 찾는 그림 Pnumber 1,2,3의 집합을 만들어 내는 쿼리문을 IN 으로 조건을 넣을 수 있다. ( 중첩 질의, sub query라고한다)
몇겹이 되든지 DBMS마다 다른 한계를 둔다. 가장 바깥 질의어를 outer query 그 뒤 중첩들은 nested query or inner query 라고한다
이미 number을 알고 있다면 다른 방식으로 표현할 수 있다는 것을 보여준다
쿼리 4 스미스가 매니저로서 참여하는 프로젝트 넘버, 스미스가 worker로 근무하는 프로젝트 넘버를 찾는다
이름은 다르지만 같은 Domain이므로 중첩 질의로 원하는 값을 찾을 수 있다.
IN 앞의 집합과 중첩질의의 집합은 결합가능 즉 두 집합은 같은 구조여야한다. 부등호 연산에 대한건 별거없다
inner쿼리와 outer 쿼리의 attribute이름의 모호성이 발생한다. 그래서 기본적 sql룰은 가장 안에 있는 table의 attribute로 간주를 한다.
직원의 부양 가족 중 이름과 성별이 같은 직원을 검색하라는 쿼리 (Franklin만 존재)

 

쿼리 16 직원이름 검색 후 그 직원의 부양가족 중 Fname과 성별이 같은 직원이 있는지 검색해보자
쿼리 16 직원이름 검색 후 그 직원의 부양가족 중 Fname과 성별이 같은 직원이 있는지 검색해보자 , 쿼리문을 일단 순차적으로 접근해보면 주민번호를 검색할텐데 IN 내부의 조건은 직원의 Fname과 부양가족의 Fname 그리고 성별이 같은 사람만을 검색한다. (여기서 Sex는 두 테이블에 존재하여 혼동을 주지만 앞서 언급한 약속때문에 가장 안쪽의 table의 attribute가 된다)
sub query입장에서 WHERE의 E.Ssn에서 E라는 table을 정해버렸기 때문에 그 후 table의 attribute들값들은 상수취급을 당한다는 내용이다. sub query는 outer query의 tuple 개수만큼 수행된다.

Correlated Nested Queries

 

WHERE문의 선언이 outer query의 attribute를 참조하고 있는경우 correlated queries 라고함

-outer query의 각 튜플마다 nested query가 수행된다 (비효율적)
- = , IN 연산자를 포함하는 nested query는 single block query로 항상 바꿔줄 수 있다.

correlated nested query를 single block query로 변경해 주는 모습이다.
exist , null이 아니면 true 반환 그렇지 않으면 false 반환
부양가족 없는사람 찾기 NOT EXISTS 사용

 
UNIQUE(Q) 함수

 

직원의 부양가족의 성별의 중복을 검사한다 그림 중복이 되지 않는 케이스만 출력한다
쿼리7 적어도 한명의 부양가족을 갖는 매니저의 이름 리스트

 

EXISTS 문 2개를 AND연산을 통해 교집합을 찾아낸다.
Research 부서 사람들의 Dno를 모를때 그것을 찾아내 사용하는 쿼리문을 보여준다. nested query를 이용한 delete , update 사용하는 모습.
Renaming attribute 해주는 모습 (재작명)


sql에서 사용하는 다양한 join 개념

Q1A , where에 join condition 대신 From에 Join table을 사용하였다. 그림 사용법 두 테이블을 JOIN 후, ON 을 이용해 condition을 넣는다.
쿼리문이 훨씬 간결해졌다.

Join의 타입 : NATURAL JOIN, OUTER JOIN

 

-JOIN을 하는 비교연산자가 '=' 인걸 EQUIJOIN이라 한다.
-NATURAL JOIN은 이것의 특별한 형태이며 만약 두 테이블이 NATURAL JOIN이라면 attibutes 이름이 같은 것들은 튜플 내용이 동등해야한다.
-결과에서도 어짜피 같기 때문에 attribute 집합이 한번만 나온다-.

Dno와 Dnumber끼리 natural join 발생, natural join시 attribute 이름이 같지 않다면 같게 바꾸어야 한다.
natural join시 결과가 중복이 없기때문에 깔끔해지고 찾기 편해진다.

Inner join

-매칭되는 tuple끼리만 결과에 포함된다
-inner join 종류 , =EQUIjoin - Natural join ,  세타 join(부등호, !=  같은 연산자)
-outer join 
 join 에 참가하지 못한 tuple들도 포함하여 검색 결과를 나타내고 싶을때 쓴다.

 

위는 inner join이 결과 , 아래는 outer join의 결과 ,  LEFT OUTER JOIN , EMPLOYEE 중에서 JOIN에 참가하지 못한 TUPLE들도 결과에 포함시켜라 (왼쪽)
Q8B , LEFT OUTER JOIN의 예시

Options
- Inner join (same as join)
- LEFT [OUTER] JOIN (outer 생략가능)
RIGHT는 오른쪽꺼에 대해, FULL은 양쪽 전부
-natural join 까지 5개

 

조인의 종류
multiway join의 예시
쿼리 19 모든 직원의 급여의 합, 최고 급여, 최소 급여, 평균급여 검색

집단함수

Built -in fuctions 으로 합계를 구한다던지 한다.

 

JOIN 한 결과를 나타낸 것에서 평균,맥스,민 찾는 모습
쿼리 21 ,22 직원수 검색 후 'Research'부서의 직원수 찾기(별로 어려울게 없다...)
쿼리 23 직원들 급여의 종류를 세어 보아라 DISTINCT를 이용해 중복을 제거해주는 모습

집단함수 적용시 NULL값 처리를 할때 문제가 발생, 
집단함수는 값의 collection에 적용되기 때문에 NULL값은 계산시 처음에 아예 제거하고 카운트한다
-집합에 NULL값 뿐이면 NULL값을 돌려준다
-예외, COUNT함수의 경우 개수를 세는 것이기 때문에 0을 돌려준다.

 

쿼리5 , 2명 이상의 부양가족을 갖는 직원의 이름 검색 COUNT를 이용해 WHERE문에 조건을 넣어 원하는 결과를 찾는 모습
집단 함수를 그룹튜플을 만들어 사용 가능하다. 쿼리 24. 각 부서마다, 부서 번호를 찾고, 부서의 직원수를 찾고, 그들의 급여의 평균을 낸다. EMPLOYEE를 같은 Dno를 같는 사람들끼리 그룹을 형성 후, 그 그룹의 튜플수와 평균을 구한다
결과값 내는 모습 , 그룹핑을 할때 NULL값이 있다면? NULL값을 갖는 것들끼리 그룹핑 하는 것이 아니라 각각 별도의 그룹으로 존재한다.
각 프로젝트에 대해, 프로젝트 넘버, 이름, 그리고 일하는 직원수를 검색해라. (Pnumber가 PK기 때문에 굳이 Pname을 그룹핑 할 필요는 없지만 SELECT절에는 GROUP BY에 있는 attribute나 집단함수에 있는 attribute만 존재해야한다.
두명 이상의 직원이 참가하는 프로젝트에 대한 쿼리25와 같은 정보를 알고 싶다 HAVING절 이용, 그룹핑을 한 후 필요없는 조건을 제거하는 역활을 한다.
HAVING절 이용한 모습
쿼리 27 각 프로젝트에 대해, 프로젝트 넘버,이름, 그리고 5번부서에 속한 직원들을 검색해라.
3명이상 근무하는 부서의 부서번호와 그 중 각 부서에서 연봉이 4만불이 넘는 직원의 수를 계산해라. 그림 SQL쿼리의 순서가 중요하다. SQL은 WHERE절이 먼저, HAVING절이 나중에 적용되기 때문에 COUNT값이 왜곡이 된다.
정답~

'Database' 카테고리의 다른 글

Database 8장  (0) 2020.10.10
Database 7장-2  (0) 2020.10.02
Database 6장-2  (0) 2020.09.19
Database 6장-1  (0) 2020.09.11
Database 5장  (0) 2020.09.07