Bollinger Bands® (John Bollinger) — a period-bar simple moving average
(the middle band) with an upper/lower band at ±stdDev population standard
deviations. Appends three columns (${prefix}Middle / ${prefix}Upper /
${prefix}Lower); the warm-up rows emit undefined. One rolling pass
(avg + stdev) over a bar-count window.
A flat window (σ = 0) is a degenerate band, not a missing one:upper = lower = middle. The bands are defined there — middle ± k·0 —
and a chart drawing them over a stale or illiquid stretch wants the
ribbon to collapse onto the centre line, not break into segments around
an unbroken middle. undefined means warm-up only, as it does for
keltner's zero-range channel. (Until [PND-BBFLAT] the bands were
blanked at σ = 0 so that "outside the band" tests would not fire on every
bar of a flat stretch; that is the consumer's test to write —
bbUpper > bbLower — not a hole in the data.) The two derived studies
keep their own flat-window answers: bollingerBandwidth is 0
there and bollingerPercentB is undefined (a genuine 0/0). Core's
TimeSeries.baseline still blanks its upper/lower at sd === 0 — a
deliberate split: that primitive is an anomaly filter, where a zero-width
band would flag every non-equal point; this study is a chart line.
Bollinger Bands® (John Bollinger) — a
period-bar simple moving average (the middle band) with an upper/lower band at ±stdDevpopulation standard deviations. Appends three columns (${prefix}Middle/${prefix}Upper/${prefix}Lower); the warm-up rows emitundefined. One rolling pass (avg + stdev) over a bar-count window.A flat window (σ = 0) is a degenerate band, not a missing one:
upper = lower = middle. The bands are defined there —middle ± k·0— and a chart drawing them over a stale or illiquid stretch wants the ribbon to collapse onto the centre line, not break into segments around an unbroken middle.undefinedmeans warm-up only, as it does for keltner's zero-range channel. (Until [PND-BBFLAT] the bands were blanked at σ = 0 so that "outside the band" tests would not fire on every bar of a flat stretch; that is the consumer's test to write —bbUpper > bbLower— not a hole in the data.) The two derived studies keep their own flat-window answers: bollingerBandwidth is0there and bollingerPercentB isundefined(a genuine 0/0). Core'sTimeSeries.baselinestill blanks itsupper/loweratsd === 0— a deliberate split: that primitive is an anomaly filter, where a zero-width band would flag every non-equal point; this study is a chart line.