Joins Part 1: practice questions
400 questions in four levels, all on RetailMart, the practice database of this course. Write every query yourself, get it wrong, read the error, fix it. That is how it sticks.
Answers are coming soon. Post your query in the WhatsApp Community or Discord and we will check it together.
Easy 100 questions Medium 100 questions Hard 100 questions Crazy 100 questions
Core syntax, applied directly
JOIN CONCEPTUAL Q1 Difference between INNER JOIN and LEFT JOIN in one sentence. Q2 When does LEFT JOIN produce NULLs in the result? Q3 Why is RIGHT JOIN considered redundant - what's the equivalent LEFT JOIN trick? Q4 What is the anti-join pattern? Write it conceptually. Q5 Why must JOIN have an ON clause - what happens without it? Q6 What's the difference between JOIN ... ON and JOIN ... USING? Q7 In a LEFT JOIN, when WHERE filters the right-side column, what silently happens? Q8 Why does COUNT(*) over-count on a LEFT JOIN when measuring left-side rows? Q9 What's a foreign-key path - give the path from sales.order_items to core.dim_category. Q10 Why is qualifying every column (alias.column) considered best practice in JOIN queries? INNER JOIN - 2 TABLES Q11 Show every order with the customer's first name. JOIN sales.orders + customers.customers. Q12 Show every order with the store's name. JOIN sales.orders + stores.stores. Q13 Show every order_item with its product's name. JOIN sales.order_items + products.products. Q14 Show every employee with their department name. JOIN stores.employees + core.dim_department. Q15 Show every store with its region name. JOIN stores.stores + core.dim_region. Q16 Show every product with its brand name. JOIN products.products + core.dim_brand. Q17 Show every brand with its category name. JOIN core.dim_brand + core.dim_category. Q18 Show every review with the customer's full name. JOIN customers.reviews + customers.customers. Q19 Show every ticket with the customer's email. JOIN support.tickets + customers.customers. Q20 Show every ticket with the agent's name (employee). JOIN support.tickets + stores.employees. Q21 Show every loyalty member with their tier name. JOIN loyalty.members + loyalty.tiers. Q22 Show every loyalty redemption with the customer's name. Q23 Show every payment with the order_status. JOIN sales.payments + sales.orders. Q24 Show every shipment with the order's net_total. JOIN sales.shipments + sales.orders. Q25 Show every return with the order_date. JOIN sales.returns + sales.orders. Q26 Show every call with the customer name. JOIN call_center.calls + customers.customers. Q27 Show every call with the agent name. JOIN call_center.calls + stores.employees. Q28 Show every supply-chain shipment with the warehouse name. JOIN supply_chain.shipments + supply_chain.warehouses. Q29 Show every supply-chain shipment with the supplier name. JOIN supply_chain.shipments + products.suppliers. Q30 Show every inventory snapshot with the warehouse name. JOIN supply_chain.inventory_snapshots + supply_chain.warehouses. Q31 Show every work_order with the production line name. JOIN manufacture.work_orders + manufacture.production_lines. Q32 Show every transcript with the call_reason. JOIN call_center.transcripts + call_center.calls. Q33 Show every pay_slip with the employee's first name. JOIN payroll.pay_slips + stores.employees. Q34 Show every attendance entry with the employee's role. Q35 Show every expense with its category_name. JOIN finance.expenses + core.dim_expense_category. Q36 Show every order with the customer tier (Bronze/Silver/Gold/Platinum). Q37 Show every page_view with the customer's first_name (skip anonymous ones - INNER JOIN drops them automatically). Q38 Show every ad_spend record with the campaign name. JOIN marketing.ads_spend + marketing.campaigns. Q39 Show every order with the store's CITY (orders + stores). Q40 Show every customer review with the product name (reviews + products). LEFT JOIN (30) Topics: preserve all left rows; NULL for unmatched right; anti-joins Q41 ALL customers + a left join to sales.orders - show order_id (will be NULL for never-ordered customers). Q42 ALL products + LEFT JOIN to sales.order_items - flag products NEVER ordered (oi.order_item_id IS NULL). Q43 ALL employees + LEFT JOIN to support.tickets (as agent). Q44 ALL stores + LEFT JOIN to sales.orders - find stores with NO orders. Q45 ALL customers + LEFT JOIN to customers.reviews - find customers who NEVER reviewed. Q46 ALL customers + LEFT JOIN to support.tickets - find customers who NEVER raised a ticket. Q47 ALL customers + LEFT JOIN to loyalty.members - non-members appear with NULL tier_id. Q48 ALL orders + LEFT JOIN to sales.shipments - find orders without shipments. Q49 ALL orders + LEFT JOIN to sales.payments - find orders not yet paid. Q50 ALL orders + LEFT JOIN to sales.returns - find orders NEVER returned. Q51 ALL products + LEFT JOIN to customers.reviews - find products with NO reviews. Q52 ALL employees + LEFT JOIN to hr.attendance - find employees with NO attendance entries. Q53 ALL warehouses + LEFT JOIN to supply_chain.inventory_snapshots - find warehouses with NO inventory data. Q54 ALL warehouses + LEFT JOIN to supply_chain.shipments. Q55 ALL campaigns + LEFT JOIN to marketing.ads_spend - campaigns with no spend? Q56 ALL production_lines + LEFT JOIN to manufacture.work_orders. Q57 ALL departments + LEFT JOIN to stores.employees - departments with NO employees. Q58 ALL regions + LEFT JOIN to stores.stores - regions with NO stores. Q59 ALL brands + LEFT JOIN to products.products - brands with NO products. Q60 ALL categories + LEFT JOIN to core.dim_brand - categories with NO brands. Q61 ALL tiers + LEFT JOIN to loyalty.members - tiers with no members. Q62 ALL expense_categories + LEFT JOIN to finance.expenses. Q63 ALL suppliers + LEFT JOIN to products.products - suppliers with no products. Q64 Anti-join: products NEVER ordered (LEFT JOIN + WHERE order_item_id IS NULL). Q65 Anti-join: customers NEVER ordered. Q66 Anti-join: customers NEVER reviewed any product. Q67 Anti-join: orders NEVER shipped. Q68 Anti-join: customers NOT in loyalty program. Q69 Anti-join: tickets NEVER resolved (use ticket.resolved_date IS NULL - single table; but show LEFT JOIN style for practice). Q70 Anti-join: employees with NO ticket assignments. RIGHT JOIN + MULTI-TABLE (30) Topics: RIGHT JOIN basics, then 3-table INNER chains Q71 RIGHT JOIN customers.customers RIGHT JOIN sales.orders - all orders, with customer info. Q72 RIGHT JOIN stores.stores RIGHT JOIN sales.orders - same idea. Q73 RIGHT JOIN products.products RIGHT JOIN sales.order_items - every item with product info. Q74 RIGHT JOIN: same as Q71 but rewritten as a LEFT JOIN. Q75 RIGHT JOIN: same as Q72 but rewritten as a LEFT JOIN. Q76 JOIN sales.orders + customers.customers + stores.stores: order_id, customer name, store name. Q77 JOIN sales.order_items + products.products + sales.orders: item_id, product_name, order_date. Q78 JOIN products.products + core.dim_brand + core.dim_category: product, brand, category. Q79 JOIN stores.employees + stores.stores + core.dim_region: employee, store, region. Q80 JOIN stores.employees + core.dim_department + stores.stores: employee, dept_name, store_name. Q81 JOIN loyalty.members + customers.customers + loyalty.tiers: member name, tier name, points. Q82 JOIN sales.orders + customers.customers + customers.addresses: order_id, customer, city. Q83 JOIN call_center.calls + customers.customers + stores.employees: customer, agent, duration. Q84 JOIN support.tickets + customers.customers + stores.employees: customer, agent, subject. Q85 JOIN customers.reviews + customers.customers + products.products: customer, product, rating. Q86 JOIN sales.returns + sales.orders + products.products: return, order_date, product. Q87 JOIN supply_chain.shipments + supply_chain.warehouses + products.suppliers: shipment, warehouse, supplier. Q88 JOIN manufacture.work_orders + manufacture.production_lines + products.products: work_order_id, line, product. Q89 JOIN payroll.pay_slips + stores.employees + stores.stores: pay_slip, employee, store. Q90 JOIN hr.attendance + stores.employees + core.dim_department: attendance, employee, department. Q91 JOIN marketing.ads_spend + marketing.campaigns + ... bonus: just 2 tables. spend, campaign name. Q92 JOIN finance.expenses + core.dim_expense_category + (where amount > 50000). Q93 JOIN audit.application_logs + (no FK needed, single table - but show with a JOIN to a synthetic literal - skip). Instead: JOIN audit.api_requests + ... single-table query (acceptable). Q94 JOIN call_center.transcripts + call_center.calls + customers.customers: transcript_id, customer, sentiment_score. Q95 JOIN web_events.events + web_events.page_views + customers.customers: event, customer, page_url. Q96 JOIN loyalty.redemptions + customers.customers + loyalty.members + loyalty.tiers: customer, tier, redemption reward. Q97 JOIN sales.orders + customers.customers + stores.stores + core.dim_region: order, customer, store, region. Q98 JOIN sales.order_items + products.products + core.dim_brand + core.dim_category + sales.orders: item, product, brand, category, order_date. Q99 JOIN sales.orders + customers.customers + sales.payments: order_id, customer, payment_mode. Q100 JOIN sales.orders + customers.customers + sales.shipments + stores.stores: full order trace (customer + courier + store). Combined ideas, multi-step thinking
JOIN DEEPER - CONCEPTUAL Q1 Why does putting a right-table filter in WHERE silently turn a LEFT JOIN into an INNER JOIN? Q2 What is "fan-out" in JOINs - and how do you detect it? Q3 Why does COUNT(*) on a LEFT JOIN over-count when measuring left rows? Q4 Compare COUNT(left.id) vs COUNT(DISTINCT left.id) vs COUNT(*) in a LEFT JOIN. Q5 Does JOIN order (A JOIN B JOIN C vs A JOIN C JOIN B) affect the RESULT? Performance? Q6 Compare JOIN ... ON vs JOIN ... USING - which collapses the duplicate column in the result? Q7 Why is JOIN orders ON 1 = 1 not the same as CROSS JOIN - what does it produce? Q8 When does an INNER JOIN drop rows you didn't expect - name three causes. Q9 Explain how a LEFT JOIN handles three rows in the left and one in the right matching one of them. Q10 Why does ANSI SQL recommend explicit JOIN syntax over comma-separated FROM clauses? Q11 What is a "Cartesian explosion" and how do you accidentally cause one? Q12 Compare LEFT JOIN + WHERE right.key IS NULL vs NOT EXISTS - which is more readable, which is faster? Q13 Why does the PostgreSQL planner choose Hash Join vs Nested Loop based on row counts? Q14 When does INNER JOIN's row count equal the smaller table's row count - and when does it not? Q15 Why is JOIN customers c1 JOIN customers c2 ON c1.id != c2.id typically an interview red flag? Q16 Explain why aliases (e1/e2/c1/c2) are MANDATORY in self-joins. Q17 Compare INNER JOIN vs SEMI JOIN (which PostgreSQL implements via EXISTS internally). Q18 What is an "anti semi join"? When does PostgreSQL use it? Q19 Why is the result of a JOIN with NULL keys deterministic - they never match? Q20 Explain why JOIN order matters less when JOINs are INNER but more for OUTER JOINs. Q21 What does "EQUI JOIN" mean vs "non-equi JOIN"? Give a real RetailMart non-equi example. Q22 Why is LEFT JOIN ... ON a.x = b.x AND b.y = 5 different from LEFT JOIN ... ON a.x = b.x WHERE b.y = 5? Q23 Compare USING (col) vs NATURAL JOIN - and why NATURAL JOIN is dangerous. Q24 How does the GROUP BY interact with multi-table JOINs - what counts as a "row" being grouped? Q25 Why must INNER JOIN with aggregates often be wrapped in a CTE for readability? INNER JOIN + FILTER + GROUP BY Q26 Per region (via stores), COUNT orders + SUM net_total. Q27 Per category, COUNT products. Q28 Per dim_brand, COUNT products + AVG price. Q29 Per dim_department, COUNT employees + AVG salary. Q30 Per tier (from loyalty.tiers JOIN loyalty.members), COUNT members + AVG points_balance. Q31 Per customer (JOIN orders), COUNT lifetime orders + SUM total spend. Q32 Per support agent (JOIN tickets), COUNT tickets resolved + AVG resolution time. Q33 Per product, SUM quantity sold (JOIN order_items). Q34 Per region (3-table JOIN: orders -> stores -> regions), SUM revenue. Q35 Per warehouse, SUM quantity_on_hand (JOIN inventory_snapshots latest). Q36 Per supplier (JOIN supply_chain.shipments), SUM quantity shipped. Q37 Per category (JOIN products -> dim_brand -> dim_category), SUM revenue from order_items. Q38 Per month + region (JOIN orders + stores + region + DATE_TRUNC), SUM net_total. Q39 Per courier_name (JOIN shipments -> orders), AVG delivery duration. Q40 Per agent_id (JOIN call_center.calls -> stores.employees), total call_duration. Q41 Per warehouse (3-table JOIN), TOP 3 products by quantity_on_hand. (Window function preview.) Q42 Per dim_department + store_id, COUNT employees + AVG salary. Q43 Per page_view device_type + customer's tier (JOIN page_views -> customers), COUNT page_views. Q44 Per platform + month (JOIN ads_spend -> campaigns), SUM amount. Q45 Per category + ticket_status (JOIN tickets), COUNT. Q46 Per ticket category + day_of_week (JOIN nothing - single table CASE), COUNT. Q47 Per region (JOIN dim_region -> stores -> orders), TOP 10 by revenue. Q48 Per brand_name (JOIN brand -> products -> order_items), SUM net_amount. Q49 Per category_name (JOIN to dim_category), SUM revenue. Q50 Per region_name + tier (JOIN orders, stores, regions, customers), COUNT distinct customers. LEFT JOIN EDGE CASES + ANTI-JOIN Q51 Show ALL departments with COUNT of employees (departments with 0 should appear as 0). Q52 Show ALL brands with COUNT of products. Q53 Show ALL stores with COUNT of orders (zero-order stores should appear as 0). Q54 Show ALL customers with COUNT of orders (use LEFT JOIN + COUNT right table column). Q55 Show ALL products with SUM of net_amount from order_items (zero-sale products show 0). Q56 Show ALL tiers with COUNT of members. Q57 Show ALL employees with COUNT of resolved tickets. Q58 Show ALL customers with COUNT of reviews (zero-review customers show 0). Q59 Show ALL regions with SUM revenue (zero-revenue regions appear with 0). Q60 Show ALL warehouses with SUM(quantity_on_hand). Q61 Show ALL campaigns with SUM ad_spend amount. Q62 Find customers who NEVER placed an order (anti-join). Q63 Find products NEVER ordered. Q64 Find stores with NO orders ever. Q65 Find brands with NO products. Q66 Find suppliers whose products were NEVER ordered (3-table anti-join). Q67 Find employees who NEVER appeared in support.tickets as agent. Q68 Find customers who placed orders but NEVER wrote a review. Q69 Find customers who NEVER had any interaction (orders, reviews, tickets, calls). Q70 Find orders with NO shipment record. Q71 Find orders with NO payment record. Q72 Find tickets that were NEVER assigned to an agent (agent_id IS NULL). Q73 Find warehouses that NEVER received a supply_chain.shipment. Q74 Find products that have inventory_snapshots but NO recent shipments (90 days). Q75 Find customers in loyalty.members but with NO redemptions. MULTI-TABLE CHAINS (4-5 TABLES) Q76 Order receipt: order_id, customer name, store name, product name, qty, amount (5 tables). Q77 Per customer, total spend + count of distinct stores ordered from (3 tables). Q78 Per region, count distinct customers, count distinct stores, sum revenue (4 tables). Q79 Per category, top product by units sold (5 tables + window preview). Q80 Per ticket, customer name + agent name + store of agent (4 tables). Q81 Per call, customer name + agent name + agent's store (4 tables). Q82 Per work_order, product name + production line name + days to complete (3 tables). Q83 Per page_view, customer first_name + os + device_type (2 tables - single JOIN). Q84 Per ad_spend, campaign_name + spend month + platform (2 tables). Q85 Per refund (return), order_date + customer name + product name (4 tables). Q86 Per shipment, courier_name + order's customer + store city (4 tables). Q87 Per pay_slip, employee name + department name + store_name (3 tables). Q88 Per loyalty member, customer name + tier name + lifetime orders (4 tables). Q89 Per expense, expense category name + amount + month (2 tables). Q90 Per inventory snapshot, warehouse name + product name + brand name + category name (5 tables). Q91 Per supplier, product count + supplier city + total quantity_shipped (3 tables). Q92 Customer 360deg: customer name, lifetime orders, total spend, count of reviews, count of tickets (4 LEFT JOINs + aggregates). Q93 Store 360deg: store name, region name, employee count, order count, revenue (5 tables - handle fan-out with subqueries). Q94 Per agent_id, count tickets handled + count calls handled (UNION of two sources) - preview Topic 11. Q95 Top 10 categories by revenue (5 tables: order_items -> products -> dim_brand -> dim_category + orders). Q96 Top 10 cities by total customer spend (4 tables). Q97 Top 10 suppliers by total quantity shipped to warehouses (3 tables). Q98 Per audit.api_requests endpoint, COUNT + AVG response_time (single table - but include AVG of response_time_ms grouped). Q99 Per call_reason, AVG sentiment_score from transcripts (3 tables: calls, transcripts, sentiment scope). Q100 Full order trace: order_id + customer + store + payment + shipment + first item product (6 tables, mix INNER + LEFT). Interview grade, edge cases
JOINs - CONCEPTUAL DEEP Q1 When does the planner pick Hash Join vs Merge Join vs Nested Loop? Q2 Why does adding ORDER BY join_key encourage Merge Join? Q3 Compare hash join build/probe phases - which side is hashed. Q4 What is a "broadcast join" - and does Postgres do it? Q5 Why is INNER JOIN ON a.x = b.y faster than CROSS JOIN + WHERE? (Hint: same plan in modern engines.) Q6 Why is JOIN ON a.x = b.y AND a.z = b.z faster with a composite index (x, z)? Q7 Non-equi join: WHERE a.range_start <= b.event_date <= a.range_end - give a RetailMart case. Q8 Range join in Postgres - what indexes help (GIST on tsrange)? Q9 Compare LATERAL JOIN vs correlated subquery - same idea, different syntax. Q10 Anti-join three ways: LEFT JOIN IS NULL vs NOT EXISTS vs EXCEPT. Q11 SEMI-JOIN: when does Postgres convert EXISTS to a semi-join? Q12 Fan-out: how does it create row multiplication in aggregations? Q13 How do you detect fan-out (compare COUNT(*) vs expected)? Q14 Why does GROUP BY after a fan-out join over-count SUM? Q15 Why is JOIN order irrelevant for INNER but critical for OUTER? Q16 How does the planner decide JOIN order (join_collapse_limit)? Q17 What is "estimated rows mismatch" - and why bad row estimates kill performance? Q18 Walk through a triangle inequality JOIN: a.x + b.y > c.z. Q19 Why is JOIN through a many-to-many bridge table called a "fan-out fan-in"? Q20 Compare JOIN ON (a.x, a.y) = (b.x, b.y) vs separate AND. Q21 Explain how OUTER JOIN's qualifying-side filter pushed into ON differs from WHERE. Q22 What is "join reordering" - and how does the planner explore options? Q23 Why does adding indexes BOTH sides of a JOIN help? Q24 Why is WHERE a.x = b.x (comma syntax) equivalent to INNER JOIN but missing the OUTER semantics? Q25 Walk through Postgres's "implicit JOIN" rewriting. NON-EQUI / MULTI-COL JOINS Q26 Range join: orders to campaigns running on the order_date (order_date BETWEEN start/end). Q27 Range join: orders to promotions active on the order_date. Q28 Range join: page_views to campaigns running during the view. Q29 Range join: pay_slip to its tax bracket (gross_salary BETWEEN min_salary AND max_salary). Q30 Range join: employee salary to its tax bracket. Q31 Multi-col join: order_items (via their order's store) to products.inventory on (store_id, product_id). Q32 Multi-col join: pay_slip to attendance on (employee_id, year). Q33 Multi-col join: inventory_snapshot to supply_chain.shipment on (warehouse_id, product_id, date). Q34 Multi-col join: order_items to returns on (order_id, prod_id). Q35 Join + filter: orders to the customer's DEFAULT address (customer_id AND is_default). Q36 INNER JOIN with a > predicate: line items priced above the product's list price. Q37 Triangle JOIN: three products whose two cheaper prices exceed the third (bundle pricing). Q38 JOIN where order_date is within 7 days of a campaign's start_date. Q39 JOIN where the customer's default-address city = store's city (proxy for "local order"). Q40 JOIN with a composite key derived in a CTE (clean city from addresses). Q41 Range JOIN: gaps-and-islands warmup (each order to the customer's NEXT order). Q42 JOIN orders to their shipment, keeping only Delivered shipments. Q43 JOIN orders to the customer's loyalty tier ("tier at order time" proxy). Q44 JOIN with date_trunc to align granularity (month). Q45 JOIN ON expression: orders bucketed into seasons (CASE-based). Q46 Self-equality on derived key: orders sharing the first 4 digits of order_id. Q47 Prefix self-join: products sharing the first 3 letters of product_name. Q48 Same-brand product pairs (self-join on brand_id). Q49 Chain join: product -> brand -> category. Q50 Join reviews to the product and the reviewing customer. ANTI-JOIN & SEMI-JOIN PATTERNS Q51 Anti-join 3 ways: customers never ordered (LEFT IS NULL, NOT EXISTS, EXCEPT). Q52 Anti-join: products with no reviews. Q53 Anti-join: employees never assigned a ticket as agent. Q54 Anti-join: customers with orders but no loyalty membership. Q55 Anti-join: orders with no shipment. Q56 Anti-join: ad spend rows with no matching campaign. Q57 Anti-join: inventory_snapshot rows where product no longer exists. Q58 Anti-join: pay_slips for employees no longer in stores.employees. Q59 Anti-join: tickets created by deleted customers (orphans). Q60 Anti-join: warehouses with no shipments in last 90 days. Q61 Anti-join: customers who never wrote a review for products they bought. Q62 Semi-join: customers who placed AT LEAST one order (EXISTS). Q63 Semi-join: products with ANY review. Q64 Semi-join: stores with employees AND orders AND inventory. Q65 Semi-join: agents who handled BOTH tickets AND calls. Q66 Find products sold in MULTIPLE regions (semi-join with HAVING COUNT > 1). Q67 Find customers with returns AND no follow-up order. Q68 Find suppliers who ship to ALL warehouses (relational division). Q69 Find brands present in EVERY region (relational division). Q70 Find customers who placed orders in BOTH 2024 AND 2025. Q71 Find products in inventory with no order_items linkage. Q72 Find pay_slips with no matching attendance record (same employee + year). Q73 Find campaigns with no spend rows. Q74 Find employees (agents) with NO calls handled in the last 30 days. Q75 Find shipments referencing deleted orders (FK enforce check). MULTI-TABLE CHAINS (3+ TABLES) Q76 6-table chain: order -> order_item -> product -> brand -> category -> supplier. Q77 5-table customer 360deg: customer -> order -> order_item -> product (+ review). Q78 Workforce chain: employee -> pay_slip + department + store. Q79 Marketing chain: campaign + ad spend + email engagement (clicks). Q80 Inventory chain: snapshot -> warehouse + product + supplier (+ shipment). Q81 Support chain: ticket -> customer + handling agent. Q82 Detect fan-out: COUNT(*) of orders JOIN order_items vs distinct orders. Q83 Subquery aggregation to avoid fan-out: pre-aggregate order_items into a CTE, then JOIN. Q84 Fan-in: DISTINCT cust_id COUNT among multi-unit order lines. Q85 5-table count: customer -> order -> item -> product -> brand (line items per customer). Q86 Items per order (orders x order_items, grouped). Q87 Revenue by region: region -> store -> order. Q88 Lifetime revenue per customer (customer -> order). Q89 Order value from its items (order -> order_items). Q90 Products per category: category -> brand -> product. Q91 Re-write a JOIN as EXISTS (semi-join): customers with at least one order. Q92 Convert a correlated subquery to a LEFT JOIN against a derived table. Q93 Products per supplier (supplier -> product). Q94 Use a MATERIALIZED CTE to pre-compute item totals, then join. Q95 Returns with their order and customer. Q96 Calls with their customer and handling agent. Q97 Payments with their order and customer. Q98 Orders since 2025 by store (store -> order, grouped). Q99 Build a "BI report" query: region -> store -> order, aggregated. Q100 Audit query: a customer table with metrics across multiple schemas (correlated subqueries). Production scenarios, optimisation
MEGA TABLE CHAINS Q1 8 tables: order -> items -> product -> brand -> category -> supplier -> warehouse -> region. Q2 10 tables: customer full lifecycle joining all activity. Q3 Fan-out controlled with pre-aggregation CTEs. Q4 6-table sales pipeline. Q5 6-table marketing attribution. Q6 6-table workforce / payroll. Q7 6-table support pipeline. Q8 6-table inventory & supply chain. Q9 Cross-domain JOIN: sales + marketing + support per customer. Q10 Cross-domain: HR + sales + customer per region. Q11 Order trace: order -> payment -> shipment -> delivery -> review. Q12 Customer trace: signup -> first order -> tier upgrade -> first review. Q13 Refund trace: order -> item -> return -> refund -> audit. Q14 Campaign trace: spend -> attribution -> order -> customer -> review. Q15 Ticket trace: ticket -> customer -> product -> order -> resolution. Q16 Call trace: call -> customer -> past_orders -> tickets. Q17 Web -> order trace: page_view -> session -> cart -> checkout -> order. Q18 Supplier trace: supplier -> product -> inventory -> shipment -> order_item. Q19 Pay_slip trace: employee -> attendance -> pay_slip -> bank. Q20 Region rollup: region -> store -> employee -> orders -> customers. Q21 Brand revenue chain: brand -> product -> order_item -> order -> store -> region. Q22 Loyalty chain: customer -> tier -> points -> redemption. Q23 AB-test chain: page_view -> AB -> cart -> order. Q24 Audit chain: order -> audit_log -> api_request -> app_log. Q25 Full 10-table receipt: every dimension visible. BI DASHBOARDS Q26 Executive: revenue, orders, customers, AOV per month. Q27 Regional: per region, top 5 stores by revenue. Q28 Tier dashboard: members, points, redemptions, revenue. Q29 Marketing: campaigns, spend, attributions, ROI. Q30 Customer service: tickets, calls, resolution time, CSAT. Q31 Inventory: stock by warehouse, low-stock, in-transit. Q32 Supplier: top suppliers, deliveries, late count. Q33 Brand performance: revenue, returns, avg rating. Q34 Category trends: month-over-month. Q35 Channel mix: organic vs paid vs referral. Q36 Cohort retention. Q37 Churn analysis. Q38 Refund leaderboard. Q39 Top customer LTV. Q40 Top product velocity. Q41 Employee productivity scoreboard. Q42 Warehouse throughput. Q43 Courier performance. Q44 Geographic heatmap. Q45 Device/platform mix. Q46 Hourly traffic curve. Q47 Weekly cadence. Q48 Holiday vs non-holiday compare. Q49 New vs returning customers. Q50 Full executive 1-page (30 metrics). PERFORMANCE TUNING Q51 EXPLAIN ANALYZE a 6-table JOIN. Q52 Pre-aggregate one branch into a CTE. Q53 Use MATERIALIZED CTE for fan-out control. Q54 Force partition-wise JOIN. Q55 Add INDEX on FK column. Q56 Add COVERING index. Q57 Add INCLUDE columns. Q58 Use partial index for hot subset. Q59 Use expression index for derived column. Q60 Use BRIN for time-series. Q61 Replace LEFT JOIN with NOT EXISTS for anti-join. Q62 Replace IN-subquery with JOIN. Q63 Replace EXISTS with semi-join INNER. Q64 Use LATERAL instead of correlated subquery. Q65 Add ORDER BY for Merge Join. Q66 Increase work_mem for big sort. Q67 Pre-sort via index for Merge Join. Q68 ANALYZE before heavy report. Q69 Increase stats target for skewed columns. Q70 Use extended stats for correlated columns. Q71 Set enable_nestloop = off to force hash. Q72 Set enable_hashjoin = off to force merge. Q73 Tune random_page_cost for SSD. Q74 Use parallel scan (max_parallel_workers). Q75 Benchmark before/after with pg_stat_statements. MATERIALIZED VIEWS Q76 MV: per region per month revenue. Q77 MV: per category top 10 products. Q78 MV: customer 360deg. Q79 MV: product 360deg. Q80 MV: store 360deg. Q81 REFRESH MATERIALIZED VIEW CONCURRENTLY. Q82 Schedule MV refresh via cron. Q83 Index a MV. Q84 Combine multiple MVs. Q85 Drop-and-rebuild MV when underlying changes. Q86 MV vs continuous aggregate (TimescaleDB). Q87 MV vs UI-side caching. Q88 MV with WITH NO DATA. Q89 MV depending on another MV. Q90 Incremental MV refresh (PG18 hints). Q91 Trigger-based recompute. Q92 Partition the MV. Q93 MV cost analysis. Q94 MV staleness monitoring. Q95 MV with row-level security. Q96 MV for cross-schema reports. Q97 MV for cross-database (via FDW). Q98 MV for replication-friendly reports. Q99 MV for "ad hoc" exec dashboard. Q100 Build a 5-MV pipeline: facts -> daily -> weekly -> monthly -> exec.