using KLHZ.Trader.Core.Contracts.Declisions.Dtos; using KLHZ.Trader.Core.Math.Common; namespace KLHZ.Trader.Core.Math.Declisions.Utils { public static class MovingAverage { private static (DateTime time, float value) CalcTimeWindowAverageValue(DateTime[] timestamps, float[] values, int window, int shift = 0) { var sum = values[values.Length - 1 - shift]; var count = 1; var startTime = timestamps[timestamps.Length - 1 - shift]; for (int i = 2; i < values.Length && startTime - timestamps[values.Length - i - shift] < TimeSpan.FromSeconds(window); i++) { sum += values[values.Length - i - shift]; count++; } return (startTime, sum / count); } public static TradingEventsDto CheckByWindowAverageMean(DateTime[] timestamps, float[] prices, int size, float meanfullStep = 3f) { var twav15s = new float[size]; var twav120s = new float[size]; var times = new DateTime[size]; for (int shift = 0; shift < size; shift++) { var twav15 = CalcTimeWindowAverageValue(timestamps, prices, 15, shift); var twav120 = CalcTimeWindowAverageValue(timestamps, prices, 120, shift); twav15s[size - 1 - shift] = twav15.value; twav120s[size - 1 - shift] = twav120.value; times[size - 1 - shift] = twav120.time; if (shift > 0) { var isCrossing = Lines.IsLinesCrossing( times[size - 1 - shift], times[size - 2 - shift], twav15s[size - 1 - shift], twav15s[size - 2 - shift], twav120s[size - 1 - shift], twav120s[size - 2 - shift]); if (shift == 1 && !isCrossing) //если нет пересечения скользящих средний с окном 120 и 15 секунд между //текущей и предыдущей точкой - можно не продолжать выполнение. { break; } if (shift > 1 && isCrossing) { // если фильтрация окном 120 наползает на окно 15 сверху, потенциальное время открытия лонга и закрытия шорта if (twav120s[size - 1] <= twav15s[size - 1] && twav120s[size - 2] > twav15s[size - 2]) { if (twav15s[size - 1 - shift] - twav15s[size - 1] >= meanfullStep) { return new TradingEventsDto(false, true); } } // если фильтрация окном 15 наползает на окно 120 сверху, потенциальное время закрытия лонга и возможно открытия шорта if (twav15s[size - 1] <= twav120s[size - 1] && twav15s[size - 2] > twav120s[size - 2]) { if (twav15s[size - 1 - shift] - twav15s[size - 1] <= -meanfullStep) { return new TradingEventsDto(true, false); } } } } } return new TradingEventsDto(false, false); } } }