mirror of
https://github.com/eclipse-sailing-analytics/sailing-analytics.git
synced 2026-10-29 23:37:10 +00:00
Added some confidence by datacount calculations to angle cluster polar service
This commit is contained in:
1 parent
97e7a9d183
commit
e62091996e
2 files changed
+32
-6
No files matched your search
@@ -326,8 +326,14 @@ public class PolarDataMiner {
|
|||||||
SpeedWithConfidence<Void> speedWithConfidence;
|
SpeedWithConfidence<Void> speedWithConfidence;
|
||||||
try {
|
try {
|
||||||
int convertedAngle = convertAngleIfNecessary(angle);
|
int convertedAngle = convertAngleIfNecessary(angle);
|
||||||
speedWithConfidence = speedRegressionPerAngleClusterProcessor.estimateBoatSpeed(boatClass,
|
SpeedWithConfidence<Void> regressionResult = speedRegressionPerAngleClusterProcessor.estimateBoatSpeed(boatClass,
|
||||||
new KnotSpeedImpl(windSpeed), new DegreeBearingImpl(convertedAngle));
|
new KnotSpeedImpl(windSpeed), new DegreeBearingImpl(convertedAngle));
|
||||||
|
if (regressionResult.getConfidence() > 0.1) {
|
||||||
|
speedWithConfidence = regressionResult;
|
||||||
|
} else {
|
||||||
|
// Low confidence. So put in 0 speed for chart
|
||||||
|
speedWithConfidence = new SpeedWithConfidenceImpl<Void>(new KnotSpeedImpl(0), regressionResult.getConfidence(), null);
|
||||||
|
}
|
||||||
} catch (NotEnoughDataHasBeenAddedException e) {
|
} catch (NotEnoughDataHasBeenAddedException e) {
|
||||||
// No data so put in a 0 speed with 0 confidence
|
// No data so put in a 0 speed with 0 confidence
|
||||||
speedWithConfidence = new SpeedWithConfidenceImpl<Void>(new KnotSpeedImpl(0), 0, null);
|
speedWithConfidence = new SpeedWithConfidenceImpl<Void>(new KnotSpeedImpl(0), 0, null);
|
||||||
|
|||||||
+25
-5
@@ -29,6 +29,8 @@ public class SpeedRegressionPerAngleClusterProcessor implements Processor<Groupe
|
|||||||
private static final Logger logger = Logger.getLogger(CubicRegressionPerCourseProcessor.class.getName());
|
private static final Logger logger = Logger.getLogger(CubicRegressionPerCourseProcessor.class.getName());
|
||||||
|
|
||||||
private final Map<GroupKey, IncrementalLeastSquares> regressions = new HashMap<>();
|
private final Map<GroupKey, IncrementalLeastSquares> regressions = new HashMap<>();
|
||||||
|
|
||||||
|
private final Map<BoatClass, Long> fixCountPerBoatClass = new HashMap<>();
|
||||||
|
|
||||||
private final ClusterGroup<Bearing> angleClusterGroup;
|
private final ClusterGroup<Bearing> angleClusterGroup;
|
||||||
|
|
||||||
@@ -46,6 +48,13 @@ public class SpeedRegressionPerAngleClusterProcessor implements Processor<Groupe
|
|||||||
public void processElement(GroupedDataEntry<GPSFixMovingWithPolarContext> element) {
|
public void processElement(GroupedDataEntry<GPSFixMovingWithPolarContext> element) {
|
||||||
GroupKey key = element.getKey();
|
GroupKey key = element.getKey();
|
||||||
IncrementalLeastSquares regression;
|
IncrementalLeastSquares regression;
|
||||||
|
BoatClass boatClass = element.getDataEntry().getBoatClass();
|
||||||
|
synchronized (fixCountPerBoatClass) {
|
||||||
|
if (!fixCountPerBoatClass.containsKey(boatClass)) {
|
||||||
|
fixCountPerBoatClass.put(boatClass, 0L);
|
||||||
|
}
|
||||||
|
fixCountPerBoatClass.put(boatClass, fixCountPerBoatClass.get(boatClass) + 1);
|
||||||
|
}
|
||||||
synchronized (regressions) {
|
synchronized (regressions) {
|
||||||
regression = regressions.get(key);
|
regression = regressions.get(key);
|
||||||
if (regression == null) {
|
if (regression == null) {
|
||||||
@@ -66,18 +75,29 @@ public class SpeedRegressionPerAngleClusterProcessor implements Processor<Groupe
|
|||||||
public SpeedWithConfidence<Void> estimateBoatSpeed(BoatClass boatClass, Speed windSpeed, Bearing trueWindAngle) throws NotEnoughDataHasBeenAddedException {
|
public SpeedWithConfidence<Void> estimateBoatSpeed(BoatClass boatClass, Speed windSpeed, Bearing trueWindAngle) throws NotEnoughDataHasBeenAddedException {
|
||||||
double speedSum = 0;
|
double speedSum = 0;
|
||||||
double numberOfSpeeds = 0;
|
double numberOfSpeeds = 0;
|
||||||
for (int i = -5; i <= 5; i++) {
|
long fixCount = 0;
|
||||||
|
for (int i = -2; i <= 2; i++) {
|
||||||
GroupKey key = createGroupKey(boatClass, new DegreeBearingImpl(Math.abs(trueWindAngle.getDegrees()) + i));
|
GroupKey key = createGroupKey(boatClass, new DegreeBearingImpl(Math.abs(trueWindAngle.getDegrees()) + i));
|
||||||
if (regressions.containsKey(key)) {
|
if (regressions.containsKey(key)) {
|
||||||
speedSum += regressions.get(key).getOrCreatePolynomialFunction().value(windSpeed.getKnots());
|
IncrementalLeastSquares incrementalLeastSquares = regressions.get(key);
|
||||||
numberOfSpeeds++;
|
fixCount = fixCount + incrementalLeastSquares.getNumberOfAddedPoints();
|
||||||
|
if (fixCount > 10) {
|
||||||
|
speedSum += incrementalLeastSquares.getOrCreatePolynomialFunction().value(windSpeed.getKnots());
|
||||||
|
numberOfSpeeds++;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (numberOfSpeeds < 1) {
|
fixCount = (long) (fixCount / numberOfSpeeds);
|
||||||
|
long fixCountOverall = 0;
|
||||||
|
if (numberOfSpeeds < 2 || fixCount < 10) {
|
||||||
throw new NotEnoughDataHasBeenAddedException("Not enough data has been added to Per Course Regressions");
|
throw new NotEnoughDataHasBeenAddedException("Not enough data has been added to Per Course Regressions");
|
||||||
|
} else {
|
||||||
|
synchronized (fixCountPerBoatClass) {
|
||||||
|
fixCountOverall = fixCountPerBoatClass.get(boatClass);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
Speed speed = new KnotSpeedImpl(speedSum / numberOfSpeeds);
|
Speed speed = new KnotSpeedImpl(speedSum / numberOfSpeeds);
|
||||||
return new SpeedWithConfidenceImpl<Void>(speed, /*FIXME*/ 0.5, null);
|
return new SpeedWithConfidenceImpl<Void>(speed, Math.min(1, 5.0 * ((double) fixCount / fixCountOverall)), null);
|
||||||
}
|
}
|
||||||
|
|
||||||
private GroupKey createGroupKey(final BoatClass boatClass, final Bearing angle) {
|
private GroupKey createGroupKey(final BoatClass boatClass, final Bearing angle) {
|
||||||
|
|||||||
Reference in new issue
Block a user