Articles ·
Indicators and rules: values you can check against TA-Lib and TradingView
A strategy is only as honest as the numbers it decides on. Metrand computes every indicator in the same engine for backtests, paper runs and live runs, and computes it the way the reference libraries traders already trust do, so you can check a value bar by bar.
How averages start
An exponential average needs a first value to start from. Metrand starts every one of them the way TA-Lib and
TradingView do: the first value is the plain average of the first period bars, and the average is empty until
then.
This applies to EMA, RMA (Wilder's average), DEMA, TEMA, MACD (all three of its averages), PPO, TSI, RSI, ATR and NATR. ATR's first true range is the bar's high minus its low.
Starting from the first price instead — which many engines do — produces values on the second bar that no reference library would show, and signals from them: an EMA(5)/EMA(20) crossover could fire before the slow average existed.
Other details that match TradingView:
- HMA uses
WMA(2·WMA(floor(n/2)) − WMA(n), floor(√n)). - Stoch RSI is 0 to 100, unsmoothed (TradingView's %K before its average); 50 when RSI was flat over the window.
A period that cannot mean anything is refused rather than silently changed: RSI, HMA, standard deviation, z-score, %B, linear-regression slope and historical volatility need a period of at least 2.
What "empty" means
An indicator that has not seen enough bars yet has no value. Empty means unknown, not false, and the rules built on it keep that meaning:
| Rule | Result |
|---|---|
a comparison (gt, lt, compare, in_range …) of an empty value |
empty |
rule.not of an empty value |
empty |
rule.all |
false as soon as one input is false; true when all are true; otherwise empty |
rule.any |
true as soon as one input is true; false when all are false; otherwise empty |
rule.cross_up / rule.cross_down |
empty on the first bar both lines exist — there is no earlier bar to cross from |
| an entry whose gate is empty | holds |
So not(any(...)) does not fire while its inputs are still warming up, and a crossover that happened before the slow
average existed is never reported as a fresh signal.
Comparing two values
rule.comparetakesepsas the margin the first value must clear:gtisa > b + eps,geisa ≥ b + eps,ltisa < b − eps,leisa ≤ b − eps.rule.approx_eqis true when|a − b| ≤ eps; ateps0 it is exact equality.rule.in_rangedefaults to the band 0 to 100, as the reference lists it.
Ladders of orders
A grid or martingale ladder emits several orders at once. A risk or execution node shapes a single order, so a ladder
wired through one would be dropped without a trace; such a graph is refused when you save it, with a message that says
why. A ladder can pass through decision.exit, which replaces it with one close when the exit condition fires. A
long ladder whose deepest rung would sit at or below a zero price is refused too. Ladder sizes are computed relative to
the largest rung, so even a 120-rung doubling ladder splits its total exactly instead of overflowing.
How much history a strategy needs
Each strategy's warm-up is derived from its graph:
- A window (SMA, Bollinger %B, Donchian, ROC …) needs its
period. - An exponential average needs more, so that the bars it started on stop showing in its value: 3 periods for an EMA (also inside MACD, PPO, TSI, DEMA and TEMA, per stage) and 5 for Wilder's averages (RSI, ATR, NATR, RMA). After 3 periods an EMA keeps about 0.25% of its start, Wilder's about 0.7% after 5.
- An indicator of an indicator needs both: an EMA(10) of an RSI(14) needs 5 × 14 + 3 × 10 = 100 bars.
- A cooldown adds nothing.
Backtests and live runs warm up on at least this much history before the first decision — see A backtest warms up the way a live run does.