F
Hi,
ich verwende zwei Libraries (eine binance-api und ta4j-core (... und erzwungenermaßen lombok)), aber weiß nicht genau, ob es die Funktion, die ich suche, schon gibt ... oder sie neu erstellt werden muss.
Es gibt 4-Stunden-Klines. Ich möchte nun berechnen, inwieweit alle Klines durchschnittlich in Prozent vom Durchschnittspreis abweichen, also wie die Volatilität wäre.
Skizze: https://i.postimg.cc/c1VhMV08/grafik.png , gesucht ist also jeweils die Boxhöhe.
Hier mein Ansatz:
import com.webcerebrium.binance.api.BinanceApi;
import com.webcerebrium.binance.api.BinanceApiException;
import com.webcerebrium.binance.datatype.BinanceCandlestick;
import com.webcerebrium.binance.datatype.BinanceInterval;
import com.webcerebrium.binance.datatype.BinanceSymbol;
import org.ta4j.core.BarSeries;
import org.ta4j.core.BaseBar;
import org.ta4j.core.BaseBarSeriesBuilder;
import org.ta4j.core.indicators.helpers.MedianPriceIndicator;
import org.ta4j.core.indicators.statistics.MeanDeviationIndicator;
import org.ta4j.core.indicators.statistics.StandardDeviationIndicator;
import org.ta4j.core.indicators.statistics.VarianceIndicator;
import org.ta4j.core.num.DecimalNum;
import java.lang.reflect.Field;
import java.math.BigDecimal;
import java.nio.charset.Charset;
import java.time.Duration;
import java.time.Instant;
import java.time.ZoneId;
import java.time.ZonedDateTime;
import java.util.Arrays;
import java.util.List;
import java.util.Locale;
import java.util.Scanner;
public class Main {
public record VolatilityResult(double average, double deviation, double halfDeviation, double up, double lo) { }
// private static final SimpleDateFormat sdf = new SimpleDateFormat();
private static final BinanceApi api = new BinanceApi();
public static String f(final Object dObj) {
if (dObj instanceof BigDecimal) {
return ((BigDecimal) dObj).toPlainString();
}
return String.format(Locale.ROOT, "%.9f", (Double) dObj);
}
public static void print(final VolatilityResult vr) {
System.out.println("vr.average = " + f(vr.average));
System.out.println("vr.deviation = " + f(vr.deviation));
System.out.println("vr.halfDevi = " + f(vr.halfDeviation));
System.out.println("vr.up = " + f(vr.up));
System.out.println("vr.lo = " + f(vr.lo));
}
public static BaseBar convertBinanceCandlestickToBaseBar(final BinanceCandlestick cs) {
return new BaseBar(
Duration.ofHours(4),
ZonedDateTime.ofInstant(
Instant.ofEpochMilli(cs.getOpenTime()), ZoneId.systemDefault()),
cs.getOpen(),
cs.getHigh(),
cs.getLow(),
cs.getClose(),
cs.getVolume());
}
public static List<BinanceCandlestick> getBinanceCandlesticks(final String name)
throws BinanceApiException, Exception {
//noinspection SpellCheckingInspection
BinanceSymbol ethbtc = new BinanceSymbol("ETHBTC");
Field symbol = ethbtc.getClass().getDeclaredField("symbol");
symbol.setAccessible(true);
symbol.set(ethbtc, name);
return api.klines(ethbtc, BinanceInterval.FOUR_HOURS, 31 * 6, null);
}
public static VolatilityResult getAvgVolatility1(final List<BinanceCandlestick> klines) {
int n = klines.size() - 1;
double sumAverage = 0;
double sumVolatility = 0;
for (int i = 0; i < n; i++) {
BinanceCandlestick cs = klines.get(i);
sumAverage += (cs.getHigh().doubleValue() + cs.getLow().doubleValue()) / 2;
sumVolatility += cs.getHigh().doubleValue() / cs.getLow().doubleValue();
}
double average = sumAverage / n;
double deviation = (sumVolatility / n - 1) * 100;
double halfDeviation = deviation / 2;
double up = average + average * ((sumVolatility / n - 1) / 2);
double lo = average - average * ((sumVolatility / n - 1) / 2);
return new VolatilityResult(average, deviation, halfDeviation, up, lo);
}
public static double[] getAvgVolatility2(final List<BinanceCandlestick> klines) {
int n = klines.size() - 1;
BarSeries series = new BaseBarSeriesBuilder().withName("my_series").build();
for (int i = 0; i < n; i++) {
BinanceCandlestick cs = klines.get(i);
series.addBar(convertBinanceCandlestickToBaseBar(cs));
}
MedianPriceIndicator mpi = new MedianPriceIndicator(series);
VarianceIndicator vi = new VarianceIndicator(mpi, n);
StandardDeviationIndicator sdi = new StandardDeviationIndicator(mpi, n);
MeanDeviationIndicator mdi = new MeanDeviationIndicator(mpi, n);
return new double[]{
vi.getValue(n - 1).doubleValue(),
sdi.getValue(n - 1).doubleValue(),
mdi.getValue(n - 1).doubleValue()
};
}
public static void main(final String[] args) throws BinanceApiException, Exception {
System.out.println("Enter symbol:");
String symbol = new Scanner(System.in, Charset.defaultCharset()).nextLine();
List<BinanceCandlestick> cs = getBinanceCandlesticks(symbol);
VolatilityResult v1 = getAvgVolatility1(cs);
double[] v2 = getAvgVolatility2(cs);
print(v1);
System.out.println(f(v2[0]));
System.out.println(f(v2[1]));
System.out.println(f(v2[2]));
}
}
Die Ausgabe ist für "ETHBTC" zurzeit:
Enter symbol:
ETHBTC
vr.average = 0.068484319
vr.deviation = 0.909483930
vr.halfDevi = 0.454741965
vr.up = 0.068795746
vr.lo = 0.068172892
0.000006160
0.002481983
0.002024274
... ich glaube, ich suche nach der average absolute deviation (AAD), oder?: https://en.wikipedia.org/wiki/Average_absolute_deviation