메뉴 여닫기
개인 메뉴 토글
로그인하지 않음
만약 지금 편집한다면 당신의 IP 주소가 공개될 수 있습니다.
(새 문서: 좋아요! 이번엔 Oracle에서 LATERAL 구문에 대해 초보자도 이해할 수 있게 쉽게 설명드릴게요. LATERAL은 고급 SQL 문법 중 하나지만, 한 번 이해하면 매우 강력하게 쓸 수 있는 기능입니다. ⸻ 1. LATERAL이란? 영문 정의 The LATERAL clause allows a subquery in the FROM clause to reference columns from preceding tables in the same FROM clause. 한글 정의 LATERAL은 FROM 절에 있는 서브쿼리에서 앞에 나오...)
 
편집 요약 없음
 
(같은 사용자의 중간 판 10개는 보이지 않습니다)
1번째 줄: 1번째 줄:
좋아요! 이번엔 Oracle에서 LATERAL 구문에 대해 초보자도 이해할 수 있게 쉽게 설명드릴게요. LATERAL은 고급 SQL 문법 중 하나지만, 한 번 이해하면 매우 강력하게 쓸 수 있는 기능입니다.


=== LATERAL 이란? ===
 
{{요점
1. LATERAL이란?
|내용= LATERAL이란?
 
* (영문)The LATERAL clause allows a subquery in the FROM clause to reference columns from preceding tables in the same FROM clause.
영문 정의
 
The LATERAL clause allows a subquery in the FROM clause to reference columns from preceding tables in the same FROM clause.
 
한글 정의


LATERAL은 FROM 절에 있는 서브쿼리에서 앞에 나오는 테이블의 컬럼을 사용할 수 있게 해주는 기능입니다.
* (한글) LATERAL은 FROM 절에 있는 서브쿼리에서 같은 레벨에 있는 테이블의 컬럼을 사용할 수 있게 해주는 기능입니다.(oracle12c 이전에는 FROM절에 있는 걑은 레벨의 테이블을 같은 레벨에 있는 서브쿼리에서 사용할수 없었음)
“좌측 테이블의 값을 우측 서브쿼리에서 쓸 수 있다” 라고 기억하세요.
}}




2. 왜 필요한가요?


기존에는 FROM 절의 **서브쿼리(subquery)**가 외부 테이블의 값을 참조할 수 없었어요.
=== 왜 필요한가요? ===
LATERAL을 쓰면 이 제한을 풀 수 있어, 행 단위로 동적으로 계산하거나 조인할 수 있어요.


# 기존에는 FROM 절의 **서브쿼리(subquery)**가 외부 테이블의 값을 참조할 수 없었어요.
# LATERAL을 쓰면 이 제한을 풀 수 있어, 행 단위로 동적으로 계산하거나 조인할 수 있어요.


3. 기본 문법


=== 기본 문법 ===
<source lang=sql>
SELECT ...
SELECT ...
FROM 테이블1 t,
FROM 테이블1 t,
     LATERAL (
     LATERAL (
         SELECT ... FROM ... WHERE ... t.컬럼 ...
         SELECT ... FROM ... WHERE ... t.컬럼 ...
     ) 서브
     ) A
</source>


Oracle 12c 이상에서는 LATERAL을 쓰지 않고 CROSS APPLY 또는 **OUTER APPLY**를 쓰기도 합니다. Oracle에서 CROSS APPLY = LATERAL.
* Oracle 12c 이상에서는 LATERAL을 쓰지 않고 CROSS APPLY 또는 **OUTER APPLY**를 쓰기도 합니다.  
* Oracle에서 CROSS APPLY = LATERAL.




4. 간단한 예제
=== 예제 ===


예제 테이블
예제 테이블


orders
* orders
{| class="wikitable"
! order_id !! customer_id
|-
| 1 || 100
|-
| 2 || 200
|}


order_id customer_id
* customers
1 100
{| class="wikitable"
2 200
! customer_id !! name
|-
| 100 || Alice
|-
| 200 || Bob
|-
| 300 || Charlie
|}


customers


customer_id name
100 Alice
200 Bob
300 Charlie




목표
목표
64번째 줄: 64번째 줄:


쿼리 예시
쿼리 예시
 
<source lang=sql>
SELECT o.order_id, c.name
SELECT o.order_id, c.name
FROM orders o,
FROM orders o,
72번째 줄: 72번째 줄:
         WHERE customers.customer_id = o.customer_id
         WHERE customers.customer_id = o.customer_id
     ) c;
     ) c;
</source>








결과


order_id name
* 결과
1 Alice
{| class="wikitable"
2 Bob
|-
! order_id !! name
|-
| 1 || Alice
|-
| 2 || Bob
|}




90번째 줄: 95번째 줄:


예제: 각 고객당 최근 주문 1개만 가져오기
예제: 각 고객당 최근 주문 1개만 가져오기
 
<source lang=sql>
SELECT c.customer_id, c.name, o.order_id
SELECT c.customer_id, c.name, o.order_id
FROM customers c,
FROM customers c,
101번째 줄: 106번째 줄:
     ) o;
     ) o;


</source>




106번째 줄: 112번째 줄:


6. LATERAL vs APPLY
6. LATERAL vs APPLY
{| class="wikitable"
! Oracle 구문 !! 설명
|-
| LATERAL || Oracle 12c 이상에서 사용 가능
|-
| CROSS APPLY || LATERAL과 동일 (INNER JOIN)
|-
| OUTER APPLY || LATERAL + OUTER JOIN 느낌 (NULL 허용)
|}


Oracle 구문 설명
LATERAL Oracle 12c 이상에서 사용 가능
CROSS APPLY LATERAL과 동일 (INNER JOIN)
OUTER APPLY LATERAL + OUTER JOIN 느낌 (NULL 허용)




129번째 줄: 140번째 줄:


보너스: JSON 컬럼 분해에도 유용!
보너스: JSON 컬럼 분해에도 유용!
 
<source lang=sql>
SELECT t.id, j.*
SELECT t.id, j.*
FROM my_table t,
FROM my_table t,
135번째 줄: 146번째 줄:
       COLUMNS (name VARCHAR2(100) PATH '$.name',
       COLUMNS (name VARCHAR2(100) PATH '$.name',
                 age  NUMBER      PATH '$.age')) j;
                 age  NUMBER      PATH '$.age')) j;
</source>


위 예제처럼 JSON_TABLE도 LATERAL처럼 동작합니다.
위 예제처럼 JSON_TABLE도 LATERAL처럼 동작합니다.
140번째 줄: 152번째 줄:


더 원하시면 실전 시나리오(예: JSON 배열 쪼개기, 시간대별 계산, 조건별 행 생성 등)도 설명해드릴 수 있어요. 특정 데이터 구조나 활용 목적이 있을까요?
실전 시나리오(예: JSON 배열 쪼개기, 시간대별 계산, 조건별 행 생성 등)

2025년 5월 22일 (목) 21:51 기준 최신판

LATERAL 이란?

menu_book LATERAL이란?
  • (영문)The LATERAL clause allows a subquery in the FROM clause to reference columns from preceding tables in the same FROM clause.
  • (한글) LATERAL은 FROM 절에 있는 서브쿼리에서 같은 레벨에 있는 테이블의 컬럼을 사용할 수 있게 해주는 기능입니다.(oracle12c 이전에는 FROM절에 있는 걑은 레벨의 테이블을 같은 레벨에 있는 서브쿼리에서 사용할수 없었음)



왜 필요한가요?

  1. 기존에는 FROM 절의 **서브쿼리(subquery)**가 외부 테이블의 값을 참조할 수 없었어요.
  2. LATERAL을 쓰면 이 제한을 풀 수 있어, 행 단위로 동적으로 계산하거나 조인할 수 있어요.


기본 문법

SELECT ...
FROM 테이블1 t,
     LATERAL (
         SELECT ... FROM ... WHERE ... t.컬럼 ...
     ) A
  • Oracle 12c 이상에서는 LATERAL을 쓰지 않고 CROSS APPLY 또는 **OUTER APPLY**를 쓰기도 합니다.
  • Oracle에서 CROSS APPLY = LATERAL.


예제

예제 테이블

  • orders
order_id customer_id
1 100
2 200
  • customers
customer_id name
100 Alice
200 Bob
300 Charlie



목표

orders 테이블에서 각 주문에 해당하는 고객 정보를 바로 옆에서 가져오기 (JOIN도 가능하지만, LATERAL은 더 유연한 활용이 가능)

쿼리 예시

SELECT o.order_id, c.name
FROM orders o,
     LATERAL (
         SELECT name
         FROM customers
         WHERE customers.customer_id = o.customer_id
     ) c;



  • 결과
order_id name
1 Alice
2 Bob


5. 동적으로 N개만 가져오기 (Top-N per group)

예제: 각 고객당 최근 주문 1개만 가져오기

SELECT c.customer_id, c.name, o.order_id
FROM customers c,
     LATERAL (
         SELECT order_id
         FROM orders
         WHERE orders.customer_id = c.customer_id
         ORDER BY order_id DESC
         FETCH FIRST 1 ROW ONLY
     ) o;


6. LATERAL vs APPLY

Oracle 구문 설명
LATERAL Oracle 12c 이상에서 사용 가능
CROSS APPLY LATERAL과 동일 (INNER JOIN)
OUTER APPLY LATERAL + OUTER JOIN 느낌 (NULL 허용)



7. 요약

항목 내용 목적 FROM 서브쿼리에서 앞의 테이블 값을 참조하고 싶을 때 사용 장점 각 행별로 동적인 서브쿼리 실행 가능 주 사용처 Top-N per group, JSON 파싱, 동적 컬럼 처리 등 필요 조건 Oracle 12c 이상


보너스: JSON 컬럼 분해에도 유용!

SELECT t.id, j.*
FROM my_table t,
     JSON_TABLE(t.json_col, '$[*]'
       COLUMNS (name VARCHAR2(100) PATH '$.name',
                age  NUMBER       PATH '$.age')) j;

위 예제처럼 JSON_TABLE도 LATERAL처럼 동작합니다.

실전 시나리오(예: JSON 배열 쪼개기, 시간대별 계산, 조건별 행 생성 등)