public PEAK(kdata data, Func <kdatapoint, double> f, PEAK_TYPE type, int distance = 5, bool reconfirm = true) { switch (type) { case PEAK_TYPE.low: { peak(data, (a, prev, next) => f(a) <= f(prev) && f(a) <= f(next), p => new sValue <double>(p.date, f(p)), crosstype.gold, type, distance, reconfirm); break; } case PEAK_TYPE.high: { peak(data, (a, prev, next) => f(a) >= f(prev) && f(a) >= f(next), p => new sValue <double>(p.date, f(p)), crosstype.dead, type, distance, reconfirm); break; } default: break; } }
private void peak( kdata k, Func <kdatapoint, kdatapoint, kdatapoint, bool> cmp, Func <kdatapoint, sValue <double> > ret, crosstype confirmcross, PEAK_TYPE type, int distance, bool reconfirm) { var count = k.Count; for (var i = distance + 1; i < count - distance; ++i) { var j = 1; for (; j <= distance; ++j) { if (!cmp(k[i], k[i - j], k[i + j])) { break; } } if (j > distance) { Add(ret(k[i])); } } if (reconfirm) { confirm(k, confirmcross, type); } }
public CCI(kdata data, int N) { for (int i = N - 1; i < data.Count; i++) { var point = data[i]; var section = data.Skip((i + 1) - N).Take(N); if (section.Count() < N) { break; } var TYP = (point.close + point.high + point.low) / 3; var MA = section.Select(d => (d.close + d.high + d.low) / 3).MA(); var AVEDEV = section.Select(d => (d.close + d.high + d.low) / 3).AVEDEV(); var CCI = (TYP - MA) / (0.015 * AVEDEV); //TYP:=(HIGH+LOW+CLOSE)/3; //CCI:(TYP-MA(TYP,N))/(0.015*AVEDEV(TYP,N)); this.Add(new sValue <double> { Date = point.date, Value = Math.Round(CCI, 2), }); } }
public RSV(kdata data, int N) { var RSVt_1 = 0d; for (int i = N - 1; i < data.Count; i++) { var Ct = data[i].close; var Ln = double.MaxValue; var Hn = double.MinValue; for (var j = i; j > i - N; --j) { if (data[j].low < Ln) { Ln = data[j].low; } if (data[j].high > Hn) { Hn = data[j].high; } } var RSVt = (Hn == Ln) ? RSVt_1 : ((Ct - Ln) / (Hn - Ln) * 100); RSVt_1 = RSVt; Add(new sValue <double>(data[i].date, RSVt)); } }
public void save(kdata data, string ktype) { var file = Configuration.data.kdata.file(ktype + "\\" + data.Code + ".csv"); var p = data.ToArray().ToCsv(); File.WriteAllText(file, p, Configuration.encoding.gbk); }
public JAX(kdata data, int N, int M) { var MA = new MA(data.close(), N); var MA3 = new MA(data.series(d => (2 * d.close + d.low + d.high) / 4), M); var func = new Func <kdatapoint, double, double>((d, salt) => d.close / salt * (2 * d.close + d.low + d.high) / 4); var dmaPrevValue = 0d; for (int i = M - 1; i < data.Count; i++) { var curr = data[i]; if (MA[curr.date] == 0d) { continue; } var AA = Math.Abs((2 * curr.close + curr.high + curr.low) / 4 - MA[curr.date]) / MA[curr.date]; var dmaValue = (2 * curr.close + curr.low + curr.high) / 4; var jax = AA * dmaValue + (1 - AA) * dmaPrevValue; dmaPrevValue = jax; var MA1 = data.Skip(i + 1 - M).Take(M).Select(p => func(p, jax)).Average(); var MAAA = ((MA1 - jax) / jax) / 3.0d; var TMP = MA1 - MAAA * MA1; var J = TMP <= jax ? jax : 0d; var A = TMP; var X = TMP <= jax ? TMP : 0d; Add(new jax { Date = curr.date, JAX = Math.Round(jax, 2), J = Math.Round(J, 2), A = Math.Round(A, 2), X = Math.Round(X, 2) }); } }
public PEAK(kdata data, PEAK_TYPE type, int distance = 5, bool reconfirm = true) { switch (type) { case PEAK_TYPE.low: { peak(data, (a, prev, next) => a.low <= prev.low && a.low <= next.low, p => new sValue <double>(p.date, p.low), crosstype.gold, type, distance, reconfirm); break; } case PEAK_TYPE.high: { peak(data, (a, prev, next) => a.high >= prev.high && a.high >= next.high, p => new sValue <double>(p.date, p.high), crosstype.dead, type, distance, reconfirm); break; } default: break; } }
public close_up_percent(kdata series, DateTime since) : base(series) { var s = series.Where(p1 => p1.date >= since); if (s.Any()) { var closeup = s.Count(p1 => p1.close >= p1.open); var total = s.Count(); value = Math.Round((closeup / (double)total) * 100, 2); } }
public low_to_historical_lowest(kdata series, DateTime since) : base(series) { var s = series.Where(p1 => p1.date >= since); if (s.Any()) { var current = series.Last(); var lowest = s.Min(p1 => p1.low); value = Math.Truncate((current.low / lowest - 1) * 100); } }
public BETA(kdata data, kdata index) { var q = from i in index join s in data on i.date equals s.date select new { stock = s.close, index = i.close }; var ret = SimpleRegression.Fit( pct(q.Select(p => p.index).ToArray()), pct(q.Select(p => p.stock).ToArray())); alpha = ret.Item1; beta = ret.Item2; }
public BOTTOM(kdata data) { var macd = new MACD(data.close()); var lows = new PEAK(data, PEAK_TYPE.low).Select(p => new { p.Date, p.Value, type = PEAK_TYPE.low }).ToArray(); var highs = new PEAK(data, PEAK_TYPE.high).Select(p => new { p.Date, p.Value, type = PEAK_TYPE.high }).ToArray(); var peaks = lows.Concat(highs).OrderBy(p => p.Date).ToArray(); for (var i = 0; i < peaks.Length - 3; ++i) { var a = peaks[i]; var b = peaks[i + 1]; var c = peaks[i + 2]; var d = peaks[i + 3]; if (a.type == PEAK_TYPE.low && b.type == PEAK_TYPE.high && c.type == PEAK_TYPE.low && d.type == PEAK_TYPE.high && b.Value > a.Value && c.Value < b.Value && c.Value >= a.Value && d.Value > b.Value) { //var next = macd.Where(p => p.Date > d.Date).ToArray(); //for(var k = 2; k < next.Length; ++k) //{ // if (next[k].DIF < 0 && // next[k - 1].DIF < 0 && // next[k - 2].DIF < 0 && // next[k].DIF > next[k - 1].DIF && // next[k].DIF > next[k - 2].DIF) // { // var v = data.FirstOrDefault(p=>p.date == next[k].Date); // if (v != null) // { // if (!this.Any(p => p.Date == next[k].Date)) // { // Add(next[k].Date, v.high); // } // } // break; // } //} var next = macd.cross_gold().Where(p => p.Date > d.Date).ToArray(); if (next.Any()) { Add(next.First().Date, 0); } } } }
void confirm(kdata k, crosstype confirmcross, PEAK_TYPE type) { var crosses = new MACD(k.close()).cross(); var list = new List <sValue <double> >(); DateTime?lastcrossdate = null; foreach (var peak in this) { var cross = crosses.FirstOrDefault(p => p.value.Date >= peak.Date); if (cross != null) { if (cross.type != confirmcross) { cross = crosses.FirstOrDefault(p => p.value.Date > peak.Date); } if (cross.type == confirmcross) { if (lastcrossdate == cross.value.Date) { switch (type) { case PEAK_TYPE.high: if (peak.Value > list[list.Count - 1].Value) { list.RemoveAt(list.Count - 1); list.Add(peak); } break; case PEAK_TYPE.low: if (peak.Value < list[list.Count - 1].Value) { list.RemoveAt(list.Count - 1); list.Add(peak); } break; } } else { list.Add(peak); } lastcrossdate = cross.value.Date; } } } Clear(); AddRange(list); }
public jun_xian_dou_tout(kdata series) : base(series) { if (series.Any()) { var current = series.Last(); var ma5 = (double)new MA(series.close(), 5); var ma30 = (double)new MA(series.close(), 30); var ma55 = (double)new MA(series.close(), 55); var ma120 = (double)new MA(series.close(), 120); value = ma5 >= ma30 && ma30 >= ma55 && ma55 >= ma120; } }
public QUOTATION(kdata data) { var close = data.close(); var macd = new MACD(close); var ma120 = new MA(close, 120); var q = (from a in data join m in macd on a.date equals m.Date select new { date = a.date, price = a, macd = m, ma120 = ma120[m.Date] }).ToArray(); for (var i = 0; i < q.Length; ++i) { var item = q[i]; var state = quotationstate.None; if (item.macd.MACD < 0) { state = quotationstate.调整; if (item.price.close >= item.price.open) { state = quotationstate.反弹; } } else { state = quotationstate.升; if (i - 1 > 0) { if (this[i - 1].state == quotationstate.回调 || this[i - 1].state == quotationstate.调整) { state = quotationstate.回升; } } if (item.price.close < item.price.open) { state = quotationstate.回调; } } Add(new quotation { date = item.date, state = state, position = judgePosition(state, item.price, item.ma120), strategy = judgeStrategy(state, item.price, item.ma120) }); } }
public KDJ(kdata data, int N = 9, int M1 = 3, int M2 = 3) { var rsv = new RSV(data, N); var K = new SMA(rsv, M1, 50); var D = new SMA(K, M2, 50); var J = (from k in K join d in D on k.Date equals d.Date select new sValue <double>(k.Date, 3 * k.Value - 2 * d.Value)).ToArray(); var p = from k in K join d in D on k.Date equals d.Date join j in J on k.Date equals j.Date select new kdj { Date = k.Date, K = Math.Round(k.Value, 2), D = Math.Round(d.Value, 2), J = Math.Round(j.Value, 2) }; AddRange(p.ToArray()); }
public historical_low(kdata series, DateTime since) : base(series) { var s = series.Where(p1 => p1.date >= since); if (s.Any()) { var min = double.MaxValue; foreach (var d in s) { if (d.low < min) { min = d.low; value = d; } } } }
public factor(kdata series) { }
public close_up_percent(kdata series, TimeSpan cross) : this(series, DateTime.Today - cross) { }