WHERE: boolean filters on bound rows
MATCH draws a subgraph pattern and binds variables.
WHERE then decides which of those bindings survive into later clauses.
Think of MATCH as candidate generation and WHERE as row-level predicate filtering. Labels and
relationship types already constrain shape; WHERE expresses everything else—ranges, string checks,
existence of properties, and compound logic.
Why WHERE exists separately from patterns: patterns excel at topology (which labels, which relationship types, which direction). Predicates on property values—especially ranges and multi-clause logic—read more clearly in WHERE. You can put simple equality inside a node map pattern, but the moment you need comparisons like greater-than, OR, or null tests, WHERE is the right home.
Property access uses dot notation: m.released,
p.name, m.tagline. If a property is
absent, the expression yields null. Comparison operators include
=, <>,
<, <=,
>, and >=. Logical operators are
AND, OR, and NOT. Parentheses remove ambiguity when you mix AND and OR in the same filter.
String helpers you will use constantly include STARTS WITH, ENDS WITH, CONTAINS, and case folding via
toLower() or toUpper(). Math operators
work on numeric properties such as release years. Prefer filtering in WHERE before heavy RETURN
expressions so non-matching rows can be discarded early. On the Movie graph, typical filters are
“released after year Y,” “name contains substring,” and “tagline is present.”
MATCH (m:Movie)
WHERE m.released >= 2000
AND m.tagline IS NOT NULL
// only movies from 2000+ that have a tagline property
RETURN m.title, m.released, m.tagline
ORDER BY m.released, m.title
LIMIT 10