본 게시글은
서울대학교 데이터사이언스대학원 이상원 교수님의
데이터사이언스 응용을 위한 빅데이터 및 지식관리시스템 강의를
학습을 목적으로 재구성하였습니다
앞의 수업 내용에서 DB의 개념적, 논리적 스키마와
data independence 개념에 대해 공부하며
view에 대한 내용을 배웠었다
오늘은 View와 view의 종류 중 하나인
materialized view에 대해 수업을 진행했다

우선 view에 대해서 다시 한 번 보자
view를 만들기 위해서는 SQL문으로
CREATE VIEW를 해주면 된다
view를 처음에 만들어줄 때 사용하는 table을
기본 table이라고 해서
Base Relation이라고 한다
base table은 우리가 일반적으로 생각하는 table이므로
물리적으로 storage에 저장되어있다
하지만 view의 경우는 base relation으로부터
정보를 저장하는 것이기 때문에
물리적으로 저장이 안되어있다
그래서 view를 다른 말로는
virtual relation이라고도 부른다

view에서 쿼리를 수행하는 예시이다
위에서 HighStudents라고 해서
gpa가 높은 학생들을 대상으로 View table을 만들었다
view table을 이용해서 쿼리문을 작성해도
우리는 원래 base relation인 Students 테이블에서
쿼리를 하는 것과 동일한 결과를 받아온다
이렇게 되는 이유는 우리가 view를 이용해서
쿼리를 날리면 DBMS에서 자동으로
그 쿼리를 base relation을 타고 들어가서
해당 조건으로 조회를 하도록 쿼리를 바꾸기 때문이다
위 ppt의 예시를 보면
HighStudents라는 view table에서 쿼리를 하면
DBMS는 자동으로
base relation인 Students table에서
gpa가 3.5이상인 학생들의 sid를 불러오는
쿼리로 변경한다

앞의 수업에서도 계속 강조가 되었던 내용이지만
view에서 가장 중요한건 data indepence다
view는 external schema라고 외부 스키마인데
주로 user와 상호작용하기 위한 스키마이다
data independence의 종류는
physical과 logical 두가지가 있는데
physical data independence는
물리적으로 데이터가 저장되는 장소나 형식이 바뀌어도
view나 query와 같은 스키마에는 영향을 주지 않는다는 것이고
logical data independence는
base relation이 변경되더라도 view에는 영향을 미치지 않는다는 것이다
그런데..
이건 내가 여기서 잘 이해가 안간건데
view는 물리적으로 실체가 없으므로
view를 통해 쿼리하는 모든건 결국 base relation에서 가져오는건데
영향을 안받는다는게 말이되나?
base relation에서 column이 drop되거나 alter되면
어떻게 view에 영향이 안갈 수가 있는거지? 생각했는데
gpt에 물어보니...
내 생각이 맞더라 ㅋㅋㅋㅋ
logical data independence는
base relation에 새로운 데이터가
insert, update, delete된다고 하더라도
view는 무조건 최신상태를 받아올 수 있는 것인데
이걸 logical data independence라고 하는 것이고
base relation의 스키마 자체가 변경되는 경우
(alter, drop)가 발생하면
그건 view에서 에러뜬다고한다
(그럼 독립성이 없는거 아님?)

아무튼 이전 수업시간에도 한 번 나왔었는데
view를 사용하면 DB의 보안을 지킬 수 있다
사용자에게 전체 테이블을 보여주고 싶지 않을 때
일부만 보여주는 것이 가능하기 때문이다
전체 table에서 특정 column 혹은 특정 tuple만
접근하도록 할 수 있는
content-based access control이 가능하다

그렇다면 view를 이용해서 데이터를 변경하는
insert, delete, update는 가능할까?
이상적으로는 모든 변경이 가능해야하지만 그렇지는 않고
특정 조건에 대해서는 변경이 안된다고한다
가장 대표적인 안되는 사례는
Aggregate Function인 Sum, Avg, Count 등이
포함되는 경우이다
그래서 oracle에서는 view에서 insert 혹은 delete를 수행할 때
view의 조건을 항상 만족하는지 체크하는
WITH CHECK OPTION이 있다
WITH CHECK OPTION을 사용하면
view의 조건을 벗어나는 쿼리를 방지할 수 있다

그럼 위에서 sum이나 avg같은 aggregate function이 있는 경우
view에서의 dml 쿼리가 불가능하다고 했는데
그럼 view를 통해서 aggregate function을 수행할 수 있는 다른 방법은 없을까?
그 방법이 바로 materialized view이다
Materalized View는 일반적인 view와 달리
쿼리의 결과를 실제 table에 저장하여
크고 복잡한 데이터의 연산을 빠르게 처리할 수 있는 view이다
여기서 가장 기억해야할 점은
Materialized View는
실제 물리적인 table이 있다는 점이다
현재 시점의 Table을 대상으로 복잡한 쿼리를 수행한 후
그 결과를 table에 미리 저장해두는 것인데
일반적으로 min, max, average, sum과 같은
통계와 관련된 작업들을 자주 수행한다
자주 사용되는 통계 데이터에 대해서
Materialized View로 저장을 해놓는 것이다
앞의 설명을 들었으면 당연히 알겠지만
Materialized View(MV)는
당연히 trade off가 존재한다
MV를 생성하는 이유는
복잡한 쿼리, 특히 통계와 같이 연산에 관련된 것은
매번 필요할때마다 수행하게 되면
수행 시간도 오래걸리고 컴퓨터 자원도 많이 사용하게된다
그래서 MV를 만든다는 것은
복잡한 쿼리를 수행할 때마다 매번 발생하는 컴퓨팅을
storage에 미리 저장해둬서 복잡한 컴퓨터 연산을
피하거나 단축시키겠다는 뜻이다
하지만 당연히 이것에 대한 단점은
하드디스크의 용량을 그만큼 차지한다는 것이다
왜냐면 MV는 물리적으로 저장되는 table이기 때문이다

위 쿼리는 Materialized View를 만드는 예시이다
MV의 이름은 product_sales_mv이고
밑에 옵션을 간단하게 살펴보자
BUILD DEFERRED는 지금 즉시 데이터를 로드하지말고
refresh 명령어를 실행했을 때
view에 데이터를 채워달라는 뜻이다
REFRESH COMPLETE는 전체 데이터를 삭제하고
다시 insert하는 방식을 뜻하는데
비효율적일수있지만 정확한 데이터를 반영할 수 있다
마지막 ENABLE QUERY REWRITE는
optimizer가 기존 쿼리를 받았을 때
MV를 사용하여 자동으로 최적화할 수 있도록
허용하는 것이다
또한, MV는 일반 base table과 동일하게
물리적으로 저장공간을 차지하는 테이블이기때문에
index table 생성도 가능하고
데이터가 커지면 partition도 가능하다

위는 오라클에서 MV를 사용하는 시나리오이다
쿼리를 위에서부터 한 번 자세히 살펴보자
우선 scott/tiger라는 계정으로 로그인을 해준다
그런 다음 scott에게 Materialized View를 생성할 수 있는 권한을 준다
그런 다음 Materialized View를 생성하는데
BUILD IMMEDIATE는 즉시 데이터를 넣어달라는 뜻이고
REFRESH FORCE는 업데이트가 수행되었을 때
Fast(변경된 데이터만)와 Complete(전체 다시 계산) 중에서
가능하면 Fast로 하지만 안될 때 Complete로 계산해달라는 뜻이다
ON DEMAND는 데이터가 변경되었을 때
명시적으로 refresh 명령을 수행해야만 변경된 데이터가 반영이 되는 것이고
ON COMMIT으로 해주면 자동으로 반영해준다
그리고 마지막 ENABLE QUERY REWRITE은
위에서 말했다시피 쿼리를 수행했을 때 optimizer가 알아서
MV를 사용하도록 설정해주는 것이다
그런 다음
EXEC DBMS_STATS.gather_table_stats문을 이용해서
optimizer가 MV를 효율적으로 사용할 수 있도록
통계정보를 업데이트해준다
그런 다음 SELECT문을 통해서 emp table을 사용하여
부서별 급여 합계를 계산하는 쿼리를 작성한다
그리고 이 쿼리를 수행했을 때
base table인 emp에서 수행하는지
emp_aggr_mv에서 수행하는지 체크한다
그런 다음 아래에서 emp 테이블에 새로운 row를
insert해준다
하지만 우리가 MV를 생성할 때
ON DEMAND로 생성해줬기 때문에
데이터를 insert하더라도 refresh 명령을 수행하지 않으면
새로 추가된 row가 반영되지 않는다
그래서 아래에서 EXEC DBMS_MVIEW.refresh를 통해
새로 insert한 row를 MV에 반영해준다
그러너 다음 다시 SELECT문을 사용해 조회하면
아마 해당 조회는 emp_aggr_mv를 사용해
조회할 확률이 더 높아질것이다

그렇다면 MV 사용 시 고려해야할
기술적인 issue들을 알아보자
우선 가장 먼저 고민해야하는 것은
어떤 view를 MV로 만들것인가이다
복잡한 쿼리가 자주 시행되는 table인지
Group by, Join과 같은 aggregate function이
자주 사용되는 table인짖
혹은 변경이 자주되면 refresh를 자주해줘야되어서
MV 생성에 적절하지 않은 view일수있기때문에
변경 빈도도 고려해줘야할 요소가 된다
다음으로는 MV가 있으면 쿼리 작성 시
우리가 MV를 자동으로 사용할 수 있으며
MV를 사용하여 최적화 할 수 있는가?이다
마지막으로는 갱신에 관한 고민이다
MV를 생성할 때는 기존 테이블에서 변경되는 데이터에 대해
어떤 방식으로 갱신할 것인지
충분히 고민해야한다

MV말고도 2020년대에 들어서
새롭게 나온 view에 대해 알아보자
oracle에서 새롭게 지원하는 view는
Oracle JSON Relational Duality라고
RDB형식으로 저장되어있는 데이터를
JSON 형식으로 쓰고 읽을 수 있도록 해주는 기능이다
내부에서는 table 형태로 저장하지만
읽을 때, 쓸 때는 모두 json 형식으로 변환해서
json 형식으로 데이터가 저장되어있는 것처럼 보이게 한다
아래는 Normalized table와 Nested table에 대한 예시인데
RDB에서 정규화에 대해서 많이 들어봤을 것이다
RDB 정규화에서 가장 핵심이 되는 개념은
중복방지인데, 이 중복방지를 위해
데이터를 여러 table로 쪼개서 나눠서 저장하게된다
이게 바로 normalized table이고
하지만 이런 방식으로 하면 join 연산을 자주 수행해야해서
쿼리 성능을 악화시킬 수 있다
따라서 join 연산이 많이 수행되는
특정 table에 한해서
중첩된 관계를 저장하도록 허용하는 것이 nested table이다

그렇다면 기존에 view가 존재하는 base table을
drop하면 어떻게 될까?
해당 base table만 사라지고
view는 삭제되지않는다
따라서 DROP TABLE할 때 뒤에 CASCADE 옵션을 넣어줘야
table과 함께 view도 삭제가 가능하다
그리고 잠깐 Delete와 Truncate와 Drop의 차이점에 대해서 살펴보자
다들 알겠지만 delete는 table 내부의 데이터에 대해 삭제하는 sql이고
drop은 테이블 자체를 삭제하는 sql이다
delete를 할 때 where를 사용하지 않으면
table에 있는 전체 row가 삭제되게된다
그렇다면 truncate은 무엇일까
truncate은 drop과는 다르게 테이블 자체를 삭제하지않고
테이블의 스키마는 그대로 유지하면서 내부 데이터만
초기화시키는 명령어이다
where를 쓰지 않은 delete와 결과는 똑같지만
수행속도는 truncate가 훨씬 빠르다

지금까지 배운 내용에 대해서 간단하게 정리해보자
Relational Model의 structure는
tablular 형식으로 데이터를 표현하는 방식이다
그런 다음 sql이라는 쿼리 언어를 통해
데이터를 조회 및 변경한다
또, DBMS에는 각종 constraint가 있는데
pk, fk에 대한 내용들을 배웠었다
'강의 > database' 카테고리의 다른 글
[database] Relational Algebra (Division과 Query 예시) (0) | 2025.03.31 |
---|---|
[database] Relational Algebra (selection, projection, cross-product, set-difference, union) (0) | 2025.03.24 |
[database] Relational Database(Primary key와 Foreign key) (0) | 2025.03.16 |
[database] DBMS는 무엇이며 왜 사용할까? (Feat. Data Independence, RDBMS) (2) | 2025.03.12 |
[database] DB는 왜 배우는가 + 데이터베이스의 역사 (0) | 2025.03.04 |