A statistical study that averages historical returns by calendar slot — day of week, month of year, or hour of day — to describe recurring patterns in past data.
Seasonality analysis groups historical price changes by a calendar dimension — day of the week, month of the year, hour of the day, or day of the month — and averages the returns within each group. The output is a profile such as 'the average Tuesday close-to-close change over the last 500 trading days' for each weekday. Unlike a plotted line indicator, seasonality is a summary statistic: it condenses many past observations into one number per calendar slot. Analysts use it to describe tendencies like month-end flows, session-open volatility, or the much-discussed monthly effects in equities. It is important to be precise about what this is: a backward-looking average of noisy data, not a forecast. An average is not a guarantee — a positive 'average Friday' can coexist with many sharply negative Fridays, and a pattern measured in one sample can vanish in the next. Seasonality output is educational, descriptive context only, not financial advice, and trading involves risk of loss regardless of what any historical average shows.
The mechanics are deterministic averaging. First choose a return definition — typically the percentage close-to-close change of each bar, which keeps observations comparable across price levels. Second, choose a calendar bucket: on a daily chart, the weekday of each bar; on a monthly view, the calendar month; on intraday charts, the hour or session. Each bar's return is added to its bucket's running sum, and a count is kept per bucket. The seasonal value for a bucket is its sum divided by its count — a plain arithmetic mean. Done correctly, this must respect the chart's timezone (a 'Monday' in exchange time may differ from UTC), handle holidays and missing sessions by simply skipping them rather than filling zeros, and use only confirmed bars so the current forming bar does not distort the average. The critical statistical caveat is the multiple-comparisons problem: if you scan seven weekdays, twelve months, thirty-one days-of-month, and twenty-four hours, you are running dozens of implicit tests, and some buckets will look impressive purely by chance. With roughly 100 observations per weekday bucket, the standard error of the mean is often as large as the mean itself — which is why honest seasonality work reports sample sizes and dispersion, not just the averages.
There are no standard indicator settings, only study choices: the return definition (close-to-close percentage change is common), the calendar bucket (weekday on daily charts, month on monthly views, hour or session intraday), and the lookback window (for example 2-5 years of daily bars, giving very roughly 100-250 observations per weekday). Longer lookbacks give larger samples but mix in older market regimes; shorter ones are more current but statistically weaker. The chart timezone setting materially changes intraday and weekday bucketing and should always be stated with any result.
//@version=6
indicator("Day-of-Week Average Return", overlay = false)
// Accumulates the average close-to-close % change per weekday.
// Descriptive statistics only - averages of past data, not forecasts.
var float[] sums = array.new_float(7, 0.0)
var int[] counts = array.new_int(7, 0)
pctChange = 100.0 * ta.change(close) / close[1]
if barstate.isconfirmed and not na(pctChange)
idx = dayofweek - 1 // 1 = Sunday ... 7 = Saturday
array.set(sums, idx, array.get(sums, idx) + pctChange)
array.set(counts, idx, array.get(counts, idx) + 1)
todayIdx = dayofweek - 1
n = array.get(counts, todayIdx)
avgToday = n > 0 ? array.get(sums, todayIdx) / n : na
plot(avgToday, "Avg % change, this weekday", color = color.blue, style = plot.style_histogram)
hline(0, "Zero", color = color.gray)Pro tip: Before trusting any seasonal pattern, count how many calendar slots you scanned to find it and divide your enthusiasm accordingly — testing dozens of buckets guarantees a few will look good by luck. Then split your history in half and check the pattern exists in both halves, and always read the average next to its sample size and spread. This is educational statistical context only, not advice: a historical average predicts nothing, and trading involves risk of loss.
Educational only — not financial advice, not a recommendation to trade. No indicator is predictive; trading involves substantial risk of loss.