// Snippet 4: the price function is compiled once to reverse-polish code, then evaluated per tick (TF_Expr.mqh) enum ENUM_TF_OP { TFOP_NUM = 0, TFOP_P, TFOP_P0, TFOP_R, TFOP_T, TFOP_D, TFOP_ADD, TFOP_SUB, TFOP_MUL, TFOP_DIV, TFOP_POW, TFOP_NEG, TFOP_ABS, TFOP_SQRT, TFOP_LN, TFOP_LOG10, TFOP_EXP, TFOP_SIN, TFOP_COS, TFOP_MIN, TFOP_MAX }; double CTFExpr::Eval(const double p, const double p0, const double t, const double d) const { double st[64]; int sp = 0; for(int i = 0; i < m_n; i++) { switch(m_op[i]) { case TFOP_NUM: st[sp++] = m_val[i]; break; case TFOP_P: st[sp++] = p; break; case TFOP_P0: st[sp++] = p0; break; case TFOP_R: st[sp++] = (p0 != 0.0 ? p / p0 : 0.0); break; case TFOP_T: st[sp++] = t; break; case TFOP_D: st[sp++] = d; break; case TFOP_ADD: sp--; st[sp - 1] += st[sp]; break; case TFOP_SUB: sp--; st[sp - 1] -= st[sp]; break; case TFOP_MUL: sp--; st[sp - 1] *= st[sp]; break; case TFOP_DIV: sp--; st[sp - 1] = (st[sp] != 0.0 ? st[sp - 1] / st[sp] : MathArcsin(2.0)); break; // NaN case TFOP_POW: sp--; st[sp - 1] = MathPow(st[sp - 1], st[sp]); break; // ... the other operators and functions follow the same pattern } } return (sp == 1 ? st[0] : MathArcsin(2.0)); // NaN when the program is malformed }