mql5/Scripts/Diagnostics/Test_ATR_Creation.ex5
darashikoh d12bddd4df High-level summary
TechnicalAnalysis_PME_Fixed.mqh (call it "Fixed") is oriented toward robust ATR handling and keeps indicator handles as class members with create/release helpers. It contains fallback logic for ATR creation and a manual ATR calculation if indicator creation fails.
TechnicalAnalysis_PME_Optimised.mqh (call it "Optimised") provides a richer set of analysis methods (advanced exit checks, divergence, ADX trend strength, MACD retrieval, volatility ratio) and more conservative/confirmed exit logic. It is more feature-rich for exit decision-making but uses simpler ATR handling (no manual fallback) and often creates temporary indicator handles in getters.
File / header differences
Fixed header: "Fixed Version with Proper ATR Handling".
Optimised header: "Optimized Technical Analysis for PME (v1.1) — [FIXED: Premature Exit Signals]".
Optimised defines a local enum ENUM_SIGNAL_TYPE (includes SIGNAL_EXIT); Fixed relies on similar enums but the file you provided doesn't show a local definition for ENUM_SIGNAL_TYPE — the Fixed class uses ENUM_SIGNAL_TYPE and ENUM_MARKET_CONDITION in its API (assumed defined in included headers).
Class design and indicator handle management
Fixed:
Class members: m_atr_handle, m_ma_handle, m_rsi_handle, m_sar_handle, m_macd_handle, m_bb_handle.
Has CreateIndicators() and ReleaseIndicators() helper methods to create and clean up member indicator handles.
Initialize() calls CreateIndicators() and returns true (even if some indicators fail). It logs warnings and does not fail initialization on missing indicators.
GetATR prefers the member m_atr_handle when symbol == _Symbol, otherwise creates a temporary handle; if indicators fail, it contains a manual ATR calculation fallback (averaging TR).
Optimised:
Class members: same set, initialized in Initialize, released in destructor.
Initialize() creates the indicators directly (no separate CreateIndicators function). It returns success boolean only if essential indicators were created (checks m_atr_handle, m_ma_handle, m_rsi_handle).
GetATR creates a temporary handle every time (iATR(symbol,...)), copies the buffer and releases the handle — no manual ATR fallback.
Destructor explicitly releases any member indicator handles.
Implication: Fixed is more defensive about indicator creation and provides fallback ATR computation for resilience on limited indicator support or resource errors. Optimised is simpler/leaner but will return 0 if ATR creation fails (no manual fallback).

ATR handling — biggest behavioral difference
Fixed:
CreateIndicators() includes multiple fallback attempts for ATR: tries _Symbol, NULL, then an alternate timeframe (PERIOD_M1). It logs each attempt and can still succeed in alternate ways.
If CopyBuffer from a temporary handle fails, Fixed then computes ATR manually using True Range over past 14 bars (using iHigh/iLow/iClose).
In GetATR, if the member handle is valid and symbol == _Symbol, it uses the cached handle and CopyBuffer for efficiency.
Optimised:
GetATR simply creates a handle with iATR(symbol,...), copies buffer, releases it; if handle invalid or copy fails, returns 0.
Initialize creates m_atr_handle but GetATR doesn't use the member handle — it creates a new one every call.
Implication: Fixed will be more robust in environments where indicator handles sometimes fail; Optimised is simpler and possibly slower (creating/releasing handles each call) but straightforward.

Methods and API surface differences
Methods present in Fixed but not (or different) in Optimised:
Fixed: GetSignal(string) — Implements a simple scoring system using RSI, MA, SAR and returns ENUM_SIGNAL_TYPE (SIGNAL_BUY/SELL/NONE).
Fixed: GetMarketCondition(), GetOptimalStop(), GetOptimalTarget(), FindKeyLevels() — present in both but implementations differ slightly.
Methods present in Optimised (new/advanced) not in Fixed:
CheckExitSignal(string, ENUM_ORDER_TYPE, double entry_price, double current_price) — multi-confirmation exit logic (requires multiple signals).
CheckExitSignalAdvanced(...) — adds bars_in_trade and profit_points filters to avoid exiting early.
IsStrongReversal(string, ENUM_ORDER_TYPE) — checks BB bands, RSI extremes and MA crosses to detect strong reversals.
IsDivergence(string, ENUM_ORDER_TYPE) — simplified divergence detection using RSI history and price series.
GetMACD(string, int &signal_line) — returns MACD value and signal line (signal_line scaled to int points in code).
GetVolatilityRatio(), GetTrendStrength() (uses ADX).
Optimised includes GetMomentum but with different calculation (percent change vs Fixed's ratio-based result).
Fixed includes CreateIndicators() and ReleaseIndicators() which centralize handle management.
Implication: Optimised introduces more sophisticated exit/confirmation logic, better for preventing premature exits (as comment indicated). Fixed focuses on indicator reliability.

Exit logic and confirmation strategy
Fixed's GetSignal is a straightforward scoring system (bull/bear scores) and returns simple signals.
Optimised's CheckExitSignal/Advanced require multiple confirmations (SIGNALS_REQUIRED=2), use stricter thresholds (e.g., RSI > 80 / < 20), consider trade age and profit when allowing exits (bars_in_trade, profit_points), and include divergence and strong reversal filters.
Implication: Optimised is conservative about exits (helps avoid chopping out of trades); Fixed provides basic signals that may produce earlier exits.

Momentum and volatility calculations
Fixed:
GetMomentum returns (close_now / close_before) * 100 (so 100 means unchanged).
GetVolatility returns ATR as percentage of price: (atr / price) * 100.
Optimised:
GetMomentum returns percent change: ((close_now - close_past) / close_past) * 100.
GetVolatility returns ATR (not converted to percent) in one place and GetVolatilityRatio returns current_atr / avg_atr by averaging last 20 ATR values.
Also has GetTrendStrength using ADX.
Implication: Numeric scales differ (Fixed's momentum centers at 100; Optimised centers at 0). If other code consumes GetMomentum, that difference can cause misinterpretation.

Resource usage and performance
Fixed caches handles and uses member handles where possible; it also has code paths to manually compute ATR (no handle allocations).
Optimised sometimes creates and destroys temporary handles per-call (e.g., GetATR, GetMA, GetMACD), which is simpler but creates overhead. However Optimised also stores member handles and could be modified to use them more consistently.
Implication: Fixed may be slightly more efficient after initial CreateIndicators (and more robust), Optimised may be simpler to maintain but could be optimized to reuse handles instead of creating them per call.

Error handling and logging
Fixed logs detailed attempts and warns via m_utils when indicators fail; it tries fallbacks.
Optimised logs errors when handles fail but doesn't attempt alternate timeframes or manual ATR fallback. It also logs initialization success only when core indicators are present.
Implication: Fixed is built for resilience in constrained environments; Optimised expects typical environment and favors clearer failure signaling.

Specific code/behavioral differences (notable snippets)
ATR fallback (Fixed):
Manual TR loop:
for i = 1..14: compute high-low and compare with prev close to derive TR and average it.
Multiple attempts to create ATR: iATR(_Symbol), iATR(NULL), iATR(_Symbol, PERIOD_M1).
Exit condition thresholds (Optimised):
RSI thresholds tightened: 80 (exit long) and 20 (exit short) vs Fixed uses 70/30 in signal scoring.
Requires at least 2 confirmation signals before exiting.
Divergence detection (Optimised):
Uses CopyBuffer for 10 RSI historical values and CopyClose for price history; then compares bars offset (primitive but explicit).
MACD:
Optimised GetMACD returns macd_buffer[0] and scales signal_line to int points (signal_line = (int)(signal_buffer[0] * 100000)).
Fixed does not implement this exact helper (but has m_macd_handle as a member).
FindKeyLevels:
Both include round numbers and ATR/MA/SAR levels. Minor differences in ordering and resizing logic, but functionally similar.
Integration risks / things to watch for
Different numeric semantics:
GetMomentum scales differ: Fixed returns around 100 for unchanged, Optimised returns 0. Caller code must expect the right scale.
ATR semantics:
If other code expects non-zero ATR even when indicators fail, Fixed is safer due to manual fallback. Optimised may return 0 and downstream code must handle that.
Handle reuse:
Optimised often creates temporary indicator handles in getters — can be optimized or cause performance hits if called frequently (e.g., per-tick on many symbols).
Enum/API mismatch:
ENUM_SIGNAL_TYPE is declared inside Optimised; Fixed uses it — ensure consistent enum definitions and values across other included headers.
Method names and signatures:
Optimised added many methods; if you swap implementations between files, ensure callers exist or are adapted (e.g., CheckExitSignalAdvanced vs previous CheckExitSignal).
Suggested next steps
If you want the robustness of Fixed and the exit-safety of Optimised, merge the best of both:
Use Fixed's ATR fallback logic inside Optimised's GetATR (or use member handle when valid).
Keep Optimised's conservative CheckExitSignal and CheckExitSignalAdvanced.
Harmonize GetMomentum scale (pick one and adjust callers).
Prefer using member handles (create in Initialize / CreateIndicators) and use CopyBuffer on members to avoid creating/releasing handles each call.
2025-10-28 13:59:12 +00:00

15 KiB