Files
marketdata/MarketDataLib/Helper/SwingTradeHelper.cs
2024-02-22 14:52:53 -05:00

88 lines
3.4 KiB
C#

using System;
using System.Collections.Generic;
using System.Text;
using MarketData.MarketDataModel;
using MarketData.Utils;
namespace MarketData.Helper
{
public class SwingTradeHelper
{
private SwingTradeHelper()
{
}
public static SwingTrades FindSwingTrades(Prices prices,DMAPricesByDate ma21,BollingerBandElementsByDate bollingerBandElements=null)
{
SwingTrades swingTrades=new SwingTrades();
if (null == prices) return swingTrades;
prices.Sort(new PriceComparerDesc());
for (int index = 0; index < prices.Count; index++)
{
SwingTrade swingTrade = FindSwing(prices, index, ma21, bollingerBandElements);
if (null == swingTrade) continue;
swingTrades.Add(swingTrade);
}
return swingTrades;
}
private static SwingTrade FindSwing(Prices prices, int startIndex,DMAPricesByDate ma21,BollingerBandElementsByDate bollingerBandElements=null)
{
if (startIndex + 4 > prices.Count) return null;
DMAPrice maPrice = null;
Price p = prices[startIndex];
Price p1 = prices[startIndex + 1];
Price p2 = prices[startIndex + 2];
Price p3 = prices[startIndex + 3];
if(!ma21.ContainsKey(p.Date))return null;
maPrice = ma21[p.Date];
if (p1.Low >= maPrice.AVGPrice) return null;
if (!(p1.Low < p.Low && p2.Low < p1.Low && p3.Low > p2.Low)) return null;
SwingTrade swingTrade = new SwingTrade();
swingTrade.Symbol = p.Symbol;
DateGenerator dateGenerator = new DateGenerator();
if (null != bollingerBandElements && bollingerBandElements.ContainsKey(p1.Date) && bollingerBandElements.ContainsKey(p2.Date) && bollingerBandElements.ContainsKey(p3.Date))
{
BollingerBandElement b1=bollingerBandElements[p1.Date];
BollingerBandElement b2=bollingerBandElements[p2.Date];
BollingerBandElement b3 = bollingerBandElements[p3.Date];
if (p1.Low < b1.L && p2.Low < b2.L && p3.Low > b3.L)
{
swingTrade.SwingType = SwingTrade.TypeOfSwing.LongBand;
swingTrade.CandleDate = p1.Date;
swingTrade.CandleHigh = p1.High;
swingTrade.StopPrice = p1.Low;
swingTrade.CloseDate = p3.Date;
swingTrade.EntryDate = dateGenerator.FindNextBusinessDay(swingTrade.CloseDate);
return swingTrade;
}
}
DateTime? closeDate = FindCloseAboveCandle(prices, p1, startIndex + 4);
swingTrade.SwingType = SwingTrade.TypeOfSwing.Long;
swingTrade.CandleDate = p1.Date;
swingTrade.CandleHigh = p1.High;
swingTrade.StopPrice = p1.Low;
if (null != closeDate)
{
swingTrade.CloseDate = closeDate.Value;
swingTrade.EntryDate = dateGenerator.FindNextBusinessDay(swingTrade.CloseDate);
}
else
{
swingTrade.CloseDate = Utility.Epoch;
swingTrade.EntryDate = Utility.Epoch;
}
if (!swingTrade.EntryDate.Equals(Utility.Epoch) && dateGenerator.DaysBetween(swingTrade.CandleDate, swingTrade.EntryDate) > 15) return null;
return swingTrade;
}
private static DateTime? FindCloseAboveCandle(Prices prices, Price priceCandle, int startIndex)
{
if (startIndex > prices.Count) return null;
for (int index = startIndex; index < prices.Count; index++)
{
Price price = prices[index];
if (price.Close > priceCandle.High) return price.Date;
}
return null;
}
}
}