OPTIONAL MATCH#

GQL 절

MATCH와 같은 방식으로 패턴을 일치시키지만, 패턴이 아무것도 찾지 못한 입력 행을 남겨 두고 그 행에 대해서는 패턴의 변수를 null로 바인딩합니다.

개요#

OPTIONAL MATCH pattern [, pattern ] ... [ WHERE condition ]

굵게 키워드 · 기울임 직접 채우는 자리 · [ ] 생략 가능 · ... 반복 가능. 구문 표기 규약을 참고하십시오.

설명#

OPTIONAL MATCH는 MATCH와 같은 패턴을 받아 같은 방식으로 일치시킵니다. 차이는 패턴이 일치하는 것을 찾지 못했을 때 무슨 일이 일어나는가입니다. 그냥 MATCH는 그 행을 버립니다. OPTIONAL MATCH는 그 행을 남기고 패턴이 도입하는 모든 변수를 null로 바인딩합니다. LEFT JOIN에 대응하는 그래프 쪽 절입니다.

  • 이미 유효 범위에 있는 변수는 자기 값을 유지합니다. null이 될 수 있는 것은 선택적 패턴이 도입하는 변수뿐입니다.

  • OPTIONAL MATCH에 붙인 WHERE는 그 선택적 일치의 일부입니다. 패턴은 일치했지만 조건에서 걸린 행은 버려지지 않고 null과 함께 남습니다. 버리려면 절 뒤에서 WITH나 FILTER로 걸러 내십시오.

  • OPTIONAL MATCH로 쿼리를 시작하면, 패턴이 아무것도 일치시키지 못했을 때 행이 없는 것이 아니라 전부 null인 행 하나가 나옵니다.

  • 한 절 안에 쉼표로 구분한 패턴이 여럿이면 그것들은 함께 선택적입니다. 전부 일치하거나, 절 전체가 null을 내놓습니다.

매개변수#

pattern

경로 패턴이며, MATCH가 쓰는 것과 같은 구문입니다. 정점·간선·경로·ONLY 형태는 MATCH를 참고하십시오.

condition

그 일치의 일부로 평가되는 불리언 표현식입니다. 이 조건에서 걸린 행은 패턴의 변수가 null인 채로 남습니다.

예제#

모든 예제는 예제 데이터셋에서 실행됩니다.

연출 여부와 무관하게 사람을 나열하기#

MATCH (p:person) WHERE p.born > 1974
OPTIONAL MATCH (p)-[:directed]->(m:movie)
RETURN p.name AS person, m.title AS directed
ORDER BY person;
      person       | directed
-------------------+-----------
 "Neill Blomkamp"  | "Elysium"
 "Ryan Gosling"    |
 "Sam Worthington" |
(3 rows)

셋 중 둘은 아무것도 연출하지 않았으므로 그 둘에 대해 m이 null이고, 따라서 m.title도 null입니다. 둘째 줄을 그냥 MATCH로 바꾼 같은 쿼리는 한 행을 반환합니다:

MATCH (p:person) WHERE p.born > 1974
MATCH (p)-[:directed]->(m:movie)
RETURN p.name AS person, m.title AS directed
ORDER BY person;
      person      | directed
------------------+-----------
 "Neill Blomkamp" | "Elysium"
(1 row)

일치하지 못한 행만 남기기#

절 뒤에서 그 선택적 변수가 null인지 검사하십시오. 아래는 나가는 related_to 간선이 없는 공상 과학 영화를 찾습니다:

MATCH (m:movie) WHERE m.genre = 'Sci-Fi'
OPTIONAL MATCH (m)-[:related_to]->(n:movie)
WITH m, n WHERE n IS NULL
RETURN m.title AS film
ORDER BY film;
        film
---------------------
 "Avatar"
 "Blade Runner 2049"
 "Elysium"
 "Gattaca"
 "Inception"
 "The Fifth Element"
(6 rows)

WHERE가 어디에 놓이는지 보기#

Jurassic Park에는 1947년생 Sam Neill 한 명이 배우로 있습니다. 조건을 선택적 일치 안에 두면 그 영화는 배우가 null인 채로 살아남습니다:

MATCH (m:movie) WHERE m.genre = 'Adventure'
OPTIONAL MATCH (p:person)-[:acted_in]->(m) WHERE p.born > 1950
RETURN m.title AS film, p.name AS actor
ORDER BY film, actor;
      film       | actor
-----------------+-------
 "Jurassic Park" |
(1 row)

같은 조건을 절 뒤에 적용하면 그 영화는 버려집니다:

MATCH (m:movie) WHERE m.genre = 'Adventure'
OPTIONAL MATCH (p:person)-[:acted_in]->(m)
WITH m, p WHERE p.born > 1950
RETURN m.title AS film, p.name AS actor
ORDER BY film, actor;
 film | actor
------+-------
(0 rows)

선택적 일치로 쿼리를 시작하기#

OPTIONAL MATCH (m:movie {title: 'Nope'})
RETURN m;
 m
---

(1 row)

m이 null인 행 하나입니다. 여기서 그냥 MATCH를 쓰면 행이 아예 없습니다.

참고#

null인 정점의 속성을 읽으면 오류가 아니라 null이 나오므로, 패턴이 일치시키지 못한 행에서도 m.title은 안전합니다. 그 행을 알아내는 믿을 만한 방법은 변수 자체를 검사하는 것, WHERE n IS NULL입니다. 일치한 정점이라도 검사하려던 그 속성을 정당하게 갖고 있지 않을 수 있기 때문입니다.

호환성#

선택적 블록 (ISO/IEC 39075 §14.4)#

표준의 <optional match statement>는 중괄호나 소괄호로 감싼 일치 문장 블록, OPTIONAL { MATCH ... MATCH ... }도 허용합니다. AgensGraph는 MATCH 바로 앞에 오는 OPTIONAL만 받으며, 블록 형태는 구문 오류입니다. OPTIONAL은 CALL 앞에도 붙습니다.

관련 항목#

  • MATCH — 패턴 구문과 선택적이 아닌 형태

  • WHERE — 조건, 그리고 그것이 효력을 갖는 자리

  • WITH — 선택적 일치 뒤에서 걸러 내는 절

  • CALL { subquery } — OPTIONAL이 이 절 앞에도 붙는다