{"slug":"can-a-death-cross-be-bullish","qid":"whipsaw","label":"whipsaw","post_title":"can-a-death-cross-be-bullish","post_url":"/blog/can-a-death-cross-be-bullish#q-whipsaw","columns":["death_cross","golden_cross","session_count","change_pct"],"rows":[{"death_cross":"Aug 18, 2004","golden_cross":"Nov 5, 2004","session_count":56,"change_pct":6.6},{"death_cross":"Jul 19, 2006","golden_cross":"Sep 11, 2006","session_count":37,"change_pct":3.8},{"death_cross":"Dec 21, 2007","golden_cross":"Jun 23, 2009","session_count":377,"change_pct":-39.7},{"death_cross":"Jul 6, 2010","golden_cross":"Oct 22, 2010","session_count":77,"change_pct":15},{"death_cross":"Aug 12, 2011","golden_cross":"Jan 31, 2012","session_count":117,"change_pct":11.2},{"death_cross":"Aug 28, 2015","golden_cross":"Dec 17, 2015","session_count":77,"change_pct":2.8},{"death_cross":"Jan 11, 2016","golden_cross":"Apr 25, 2016","session_count":72,"change_pct":8.6},{"death_cross":"Dec 7, 2018","golden_cross":"Apr 1, 2019","session_count":77,"change_pct":8.4},{"death_cross":"Mar 30, 2020","golden_cross":"Jul 9, 2020","session_count":70,"change_pct":20.2},{"death_cross":"Mar 14, 2022","golden_cross":"Feb 2, 2023","session_count":224,"change_pct":-0.1},{"death_cross":"Apr 14, 2025","golden_cross":"Jul 1, 2025","session_count":53,"change_pct":14.6}],"shape":"ranking","sql":"WITH\nbars AS\n(\n    SELECT\n        date,\n        toFloat64(argMax(close, _ingest_time)) AS px\n    FROM global_markets.stocks_daily_aggs\n    WHERE ticker = 'SPY'\n    GROUP BY date\n),\nsmas AS\n(\n    SELECT\n        date,\n        px,\n        row_number() OVER (ORDER BY date) AS rn,\n        avg(px) OVER (ORDER BY date ROWS BETWEEN 49 PRECEDING AND CURRENT ROW) AS avg_50,\n        avg(px) OVER (ORDER BY date ROWS BETWEEN 199 PRECEDING AND CURRENT ROW) AS avg_200\n    FROM bars\n),\nstates AS\n(\n    SELECT\n        *,\n        (avg_50 < avg_200) AS below,\n        lagInFrame((avg_50 < avg_200), 1) OVER (ORDER BY date ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) AS prev_below\n    FROM smas\n),\nflags AS\n(\n    SELECT\n        *,\n        (rn >= 201 AND below = 1 AND prev_below = 0) AS is_death,\n        (rn >= 201 AND below = 0 AND prev_below = 1) AS is_golden\n    FROM states\n),\nevents AS\n(\n    SELECT date, px, rn, is_death\n    FROM flags\n    WHERE is_death OR is_golden\n),\npaired AS\n(\n    SELECT\n        date,\n        px,\n        rn,\n        is_death,\n        leadInFrame(date, 1) OVER (ORDER BY date ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) AS next_date,\n        leadInFrame(px, 1)   OVER (ORDER BY date ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) AS next_px,\n        leadInFrame(rn, 1)   OVER (ORDER BY date ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) AS next_rn\n    FROM events\n)\nSELECT\n    concat(formatDateTime(date, '%b'), ' ', toString(toDayOfMonth(date)), ', ', toString(toYear(date))) AS death_cross,\n    if(next_rn > 0,\n       concat(formatDateTime(next_date, '%b'), ' ', toString(toDayOfMonth(next_date)), ', ', toString(toYear(next_date))),\n       'none yet')                                                    AS golden_cross,\n    if(next_rn > 0, toInt64(next_rn) - toInt64(rn), NULL)             AS session_count,\n    if(next_rn > 0, round((next_px / px - 1) * 100, 1), NULL)         AS change_pct\nFROM paired\nWHERE is_death\nORDER BY date","computed_at":"2026-09-13T15:00:29.280060+00:00","elapsed":0.005618402}