Worth 21% of the SnowPro Core (COF-C03) exam — 6 subtopics.
Verified against the official Snowflake COF-C03 Exam Study Guide — follows guide sections 4.1-4.4. Streams/Tasks/Dynamic Tables moved to Domain 3 to match the official guide's own filing (they're under "automated data ingestion" there, not performance).
SNOWFLAKE.ACCOUNT_USAGE views: QUERY_HISTORY (execution details, retained longer than
INFORMATION_SCHEMA's version) and query attribution views (which warehouse/user/query tag
drove which cost) — the go-to source for retrospective performance/cost analysis.INSERT/COPY/UPDATE/DELETE). Requires enough partitions to be worth splitting and no
nondeterministic functions (RANDOM(), SEQ) in the query."ineligible", "ineligibleReason": "NO_LARGE_ENOUGH_SCAN" from
SYSTEM$ESTIMATE_QUERY_ACCELERATION(). A selective filter over a genuinely large (many
GB-TB) production table is the real target, not GB-scale data regardless of selectivity.QUERY_ACCELERATION_MAX_SCALE_FACTOR: a hard cost multiplier on the warehouse's own
rate, not a performance dial — e.g. a Medium warehouse (4 credits/hr) with scale factor 5 can
lease up to 20 additional credits/hr of QAS compute. 0 = no upper bound. Billed separately
from warehouse credits, serverless, per-second, only while in use. Default scale factor
(verified against current docs): 8 when QAS is explicitly enabled by hand, but only 2
when it's auto-enabled (Gen2/multi-cluster warehouses can auto-enable QAS) — worth knowing the
auto-enabled default is deliberately more conservative than the manual one.SYSTEM$ESTIMATE_QUERY_ACCELERATION (query_id). Check what actually happened after: QUERY_ACCELERATION_BYTES_SCANNED /
_PARTITIONS_SCANNED / _UPPER_LIMIT_SCALE_FACTOR columns in QUERY_HISTORY. Two more
monitoring surfaces worth knowing by name: the QUERY_ACCELERATION_ELIGIBLE view
(identifies which queries/warehouses would benefit most from turning QAS on) and the
QUERY_ACCELERATION_HISTORY view/table function (historical QAS billing/usage, separate
from ordinary warehouse credit consumption).IN/LIKE (verified
against current docs) — it also covers: substring and regex matches (LIKE/ILIKE/RLIKE),
NULL checks, geospatial predicates on GEOGRAPHY values, full-text search via the
SEARCH/SEARCH_IP functions, and lookups into semi-structured VARIANT/OBJECT/ARRAY
columns — not just simple scalar-column equality.
ALTER TABLE <table> ADD SEARCH OPTIMIZATION; — builds a specialized access path
asynchronously in the background, not instantly; check search_optimization_progress in
SHOW TABLES output (0-100) to see build status, and search_optimization_bytes for the
access path's storage footprint once built.SYSTEM$ESTIMATE_QUERY_ACCELERATION's sibling function,
SYSTEM$ESTIMATE_SEARCH_OPTIMIZATION_COSTS('<table>') — returns JSON with BuildCosts
(credits) and StorageCosts (TB/month) estimates. Verified hands-on: MaintenanceCosts came
back "NotAvailable" — "Table is too young. Requires 7 day(s) of history" on a brand-new
table — ongoing maintenance-cost estimation needs real observed query/write history over
time, not just the table's current size.ALTER TABLE ... CLUSTER BY (...) — keeps specified column(s) co-located
across micro-partitions as a table grows/churns, preserving pruning effectiveness. Snowflake
performs automatic reclustering in the background (consumes credits); only worth it on
large (multi-TB), frequently-filtered/joined tables — small tables see no benefit and add
needless reclustering cost.SHOW-type queries specifically, the role
must exactly match the role that generated the cached result.UUID_STRING, RANDOM,
RANDSTR), external functions, hybrid table queries, result-affecting config changes, and —
easy to miss — background reclustering/partition consolidation alone, even with no
logical data change.COUNT(*)-style results.VARIANT (max ~16MB
compressed/value, :/bracket notation, FLATTEN() to explode nested arrays/objects) +
unstructured file handling via stages/directory tables (see
Domain 3).SUM, COUNT, AVG, MIN/MAX) plus Snowflake extras
like APPROX_COUNT_DISTINCT (HyperLogLog-based, much cheaper than exact COUNT(DISTINCT) on
huge tables) and semi-structured-aware aggregates.ROW_NUMBER(), RANK(), LAG/LEAD, running totals via
OVER (PARTITION BY ... ORDER BY ...); QUALIFY lets you filter directly on a window
function's result without wrapping the query in a subquery/CTE — a Snowflake-specific
convenience worth knowing by name.SELECT * on wide tables, using QUALIFY instead of nested subqueries, and preferring
set-based operations over row-by-row procedural logic.APPROX_COUNT_DISTINCT might be preferred over exact
COUNT(DISTINCT) at scale?QUALIFY does and why it exists?Reading is not the same as being able to answer under time pressure. SnowPro Core Prep has practice questions for this domain and full-length mock exams weighted to the real split — free, open source, and explorable without an account.