tfcache
Changes
src/main/java/br/ufrgs/inf/prosoft/tfcache/Metrics.java 297(+134 -163)
Details
diff --git a/src/main/java/br/ufrgs/inf/prosoft/tfcache/metadata/Method.java b/src/main/java/br/ufrgs/inf/prosoft/tfcache/metadata/Method.java
index ae74a46..6291cfb 100755
--- a/src/main/java/br/ufrgs/inf/prosoft/tfcache/metadata/Method.java
+++ b/src/main/java/br/ufrgs/inf/prosoft/tfcache/metadata/Method.java
@@ -6,6 +6,7 @@ import br.ufrgs.inf.prosoft.tfcache.Simulator;
import br.ufrgs.inf.prosoft.tfcache.StorageManager;
import br.ufrgs.inf.prosoft.tfcache.configuration.Configuration;
+import java.math.BigDecimal;
import java.text.MessageFormat;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
@@ -22,7 +23,7 @@ public class Method {
private List<GroupOfOccurrences> groupsOfOccurrences;
private Integer countChangeableGroups;
private Pareto pareto;
- private Double minEuclideanDistance;
+ private BigDecimal normalisedMinEuclideanDistance;
public Method(String name, List<Occurrence> occurrences) {
this.name = name;
@@ -48,9 +49,10 @@ public class Method {
return name;
}
- public double getMinEuclideanDistance() {
- if (minEuclideanDistance == null) minEuclideanDistance = this.pareto.getNormalised().getMinEuclideanDistance();
- return minEuclideanDistance;
+ public BigDecimal getNormalisedMinEuclideanDistance() {
+ if (this.pareto == null) throw new RuntimeException("trying to access pareto before calculating it");
+ if (normalisedMinEuclideanDistance == null) normalisedMinEuclideanDistance = this.pareto.getNormalisedMinEuclideanDistance();
+ return normalisedMinEuclideanDistance;
}
public Metrics getBestMetrics() {
@@ -58,9 +60,9 @@ public class Method {
return this.pareto.getBestMetrics();
}
- public double getEstimatedSavedTime() {
+ public long getEstimatedSavedTime() {
if (getBestMetrics() != null) return getBestMetrics().getSavedTime();
- return groupsOfOccurrences().map(it -> it.getBestMetrics().getSavedTime()).reduce(Double::sum).orElse(0D);
+ return groupsOfOccurrences().map(it -> it.getBestMetrics().getSavedTime()).reduce(Long::sum).orElse(0L);
}
public Stream<Occurrence> occurrences() {
src/main/java/br/ufrgs/inf/prosoft/tfcache/Metrics.java 297(+134 -163)
diff --git a/src/main/java/br/ufrgs/inf/prosoft/tfcache/Metrics.java b/src/main/java/br/ufrgs/inf/prosoft/tfcache/Metrics.java
index d230722..40f3810 100755
--- a/src/main/java/br/ufrgs/inf/prosoft/tfcache/Metrics.java
+++ b/src/main/java/br/ufrgs/inf/prosoft/tfcache/Metrics.java
@@ -10,7 +10,6 @@ import br.ufrgs.inf.prosoft.tfcache.metadata.Occurrence;
import java.math.BigDecimal;
import java.math.MathContext;
-import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.stream.Collectors;
import java.util.stream.Stream;
@@ -20,167 +19,139 @@ import java.util.stream.Stream;
*/
public class Metrics implements Comparable<Metrics> {
- private long ttl;
- private long hits;
- private long timeInCache;
- private long computationTime;
- private long stales;
- private double savedTime;
-
- private transient String uuid;
- private transient Double idleTime;
-
- protected Metrics() {
- Logger.getLogger(Metrics.class.getName()).log(Level.FINEST, "returning empty metrics");
- }
-
- public Metrics(long ttl, long hits, long timeInCache, long computationTime, long stales, double savedTime, String uuid) {
- this(ttl, hits, timeInCache, computationTime, stales, savedTime);
- this.uuid = uuid;
- }
-
- public Metrics(long ttl, long hits, long timeInCache, long computationTime, long stales, double savedTime) {
- if (ttl < 0 || hits < 0 || timeInCache < 0 || computationTime < 0 || stales < 0 || savedTime < 0) {
- throw new RuntimeException("Metrics cannot be under zero."
- + " TTL: " + ttl
- + " hits: " + hits
- + " timeInCache: " + timeInCache
- + " computationTime: " + computationTime
- + " stales: " + stales
- + " savedTime: " + savedTime);
- }
- if (ttl == 0 || computationTime == 0 || timeInCache == 0) {
- throw new RuntimeException("Metrics cannot be zero."
- + " TTL: " + ttl
- + " timeInCache: " + timeInCache
- + " computationTime: " + computationTime);
- }
- this.ttl = ttl;
- this.hits = hits;
- this.timeInCache = timeInCache;
- this.computationTime = computationTime;
- this.stales = stales;
- this.savedTime = savedTime;
- }
-
- public static String getUUID(Stream<Occurrence> occurrences) {
- return occurrences.map(it -> it.getStartTime() + ":" + it.getEndTime()).collect(Collectors.joining(","));
- }
-
- private static double calculateEuclideanDistance(double x1, double y1, double x2, double y2) {
- return Math.sqrt(Math.pow(x1 - x2, 2) - Math.pow(y1, y2));
- }
-
- protected double calculateEuclideanDistance(double objectiveSavedTime, double objectiveIdleTime) {
- return calculateEuclideanDistance(getSavedTime(), getIdleTime(), objectiveSavedTime, objectiveIdleTime);
- }
-
- protected String getUUID() {
- return uuid;
- }
-
- public long getTtl() {
- return this.ttl;
- }
-
- public long getHits() {
- return this.hits;
- }
-
- public long getTimeInCache() {
- return timeInCache;
- }
-
- public double getIdleTime() {
- if (this.idleTime == null) {
- this.idleTime = (double) timeInCache - hits;
- }
- return this.idleTime;
- }
-
- public long getComputationTime() {
- return computationTime;
- }
-
- public long getStales() {
- return this.stales;
- }
-
- public double getSavedTime() {
- return this.savedTime;
- }
-
- public BigDecimal getSavedTimePerTimeInCache() {
- if (this.timeInCache + this.computationTime == 0) {
- return BigDecimal.ZERO;
- }
- return new BigDecimal(this.savedTime)
- .divide(new BigDecimal(this.timeInCache + this.computationTime), MathContext.DECIMAL128);
- }
-
- public Double getDifference() {
- return Configuration.getPreferences().get(0) * getSavedTime() - Configuration.getPreferences().get(1) * getIdleTime();
- }
-
- protected Metrics getNormalised(double savedTime, double idleTime) {
- if (savedTime < 0 || savedTime > 1) {
- throw new RuntimeException("wrong savedTime");
- }
- if (idleTime < 0 || idleTime > 1) {
- throw new RuntimeException("wrong idleTime");
- }
- Metrics metrics = new Metrics(ttl,
- hits,
- timeInCache,
- computationTime,
- stales,
- savedTime,
- uuid);
- metrics.idleTime = idleTime;
- return metrics;
- }
-
- @Override
- public int compareTo(Metrics other) {
- if (getTtl() == other.getTtl()) {
- return 0;
- }
- if (getSavedTime() == other.getSavedTime() && getIdleTime() == other.getIdleTime()) {
- throw new RuntimeException("different ttls leading to same metrics");
- }
- if (getSavedTime() >= other.getSavedTime() && getIdleTime() <= other.getIdleTime()) {
- return 1;
- }
- if (getSavedTime() <= other.getSavedTime() && getIdleTime() >= other.getIdleTime()) {
- return -1;
- }
- throw new RuntimeException("comparing pareto metrics");
- }
-
- @Override
- public int hashCode() {
- int hash = 7;
- hash = 97 * hash + (int) (this.ttl ^ (this.ttl >>> 32));
- return hash;
- }
-
- @Override
- public boolean equals(Object obj) {
- if (!(obj instanceof Metrics)) {
- return false;
- }
- return compareTo((Metrics) obj) == 0;
- }
-
- @Override
- public String toString() {
- return "TTL: " + this.ttl
- + " STpTiC: " + getSavedTimePerTimeInCache()
- + " Stales: " + this.stales
- + " Hits: " + this.hits
- + " SavedTime: " + this.savedTime
- + " TimeInCache: " + this.timeInCache
- + " ComputationTime: " + this.computationTime;
- }
+ private static final Logger LOGGER = Logger.getLogger(Metrics.class.getName());
+ private long ttl;
+ private long hits;
+ private long timeInCache;
+ private long computationTime;
+ private long stales;
+ private long savedTime;
+
+ private transient Long idleTime;
+ private transient String uuid;
+
+ protected Metrics() {
+ LOGGER.finest("returning empty metrics");
+ }
+
+ public Metrics(long ttl, long hits, long timeInCache, long computationTime, long stales, long savedTime, String uuid) {
+ this(ttl, hits, timeInCache, computationTime, stales, savedTime);
+ this.uuid = uuid;
+ }
+
+ public Metrics(long ttl, long hits, long timeInCache, long computationTime, long stales, long savedTime) {
+ if (ttl < 0 || hits < 0 || timeInCache < 0 || computationTime < 0 || stales < 0 || savedTime < 0)
+ throw new RuntimeException("Metrics cannot be under zero."
+ + " TTL: " + ttl
+ + " hits: " + hits
+ + " timeInCache: " + timeInCache
+ + " computationTime: " + computationTime
+ + " stales: " + stales
+ + " savedTime: " + savedTime);
+ if (ttl == 0 || computationTime == 0 || timeInCache == 0) throw new RuntimeException("Metrics cannot be zero."
+ + " TTL: " + ttl
+ + " timeInCache: " + timeInCache
+ + " computationTime: " + computationTime);
+ this.ttl = ttl;
+ this.hits = hits;
+ this.timeInCache = timeInCache;
+ this.computationTime = computationTime;
+ this.stales = stales;
+ this.savedTime = savedTime;
+ }
+
+ public static String getUUID(Stream<Occurrence> occurrences) {
+ return occurrences.map(it -> it.getStartTime() + ":" + it.getEndTime()).collect(Collectors.joining(","));
+ }
+
+ public static BigDecimal calculateEuclideanDistance(double x1, double y1, double x2, double y2) {
+ return BigDecimal.valueOf(x1 - x2).pow(2).add(BigDecimal.valueOf(y1 - y2).pow(2)).sqrt(MathContext.DECIMAL128);
+ }
+
+ public static BigDecimal calculateEuclideanDistance(BigDecimal x1, BigDecimal y1, double x2, double y2) {
+ return x1.subtract(BigDecimal.valueOf(x2)).pow(2)
+ .add(y1.subtract(BigDecimal.valueOf(y2)).pow(2))
+ .sqrt(MathContext.DECIMAL128);
+ }
+
+ protected BigDecimal calculateEuclideanDistance(double objectiveSavedTime, double objectiveIdleTime) {
+ return calculateEuclideanDistance(getSavedTime(), getIdleTime(), objectiveSavedTime, objectiveIdleTime);
+ }
+
+ protected String getUUID() {
+ return uuid;
+ }
+
+ public long getTtl() {
+ return this.ttl;
+ }
+
+ public long getHits() {
+ return this.hits;
+ }
+
+ public long getTimeInCache() {
+ return timeInCache;
+ }
+
+ public long getIdleTime() {
+ if (this.idleTime == null) this.idleTime = timeInCache - hits;
+ return this.idleTime;
+ }
+
+ public long getComputationTime() {
+ return computationTime;
+ }
+
+ public long getStales() {
+ return this.stales;
+ }
+
+ public long getSavedTime() {
+ return this.savedTime;
+ }
+
+ public BigDecimal getSavedTimePerTimeInCache() {
+ if (this.timeInCache + this.computationTime == 0) return BigDecimal.ZERO;
+ return BigDecimal.valueOf(this.savedTime).divide(new BigDecimal(this.timeInCache + this.computationTime), MathContext.DECIMAL128);
+ }
+
+ public Double getDifference() {
+ return Configuration.getPreferences().get(0) * getSavedTime() - Configuration.getPreferences().get(1) * getIdleTime();
+ }
+
+ @Override
+ public int compareTo(Metrics other) {
+ if (getTtl() == other.getTtl()) return 0;
+ if (getSavedTime() == other.getSavedTime() && getIdleTime() == other.getIdleTime()) throw new RuntimeException("different ttls leading to same metrics");
+ if (getSavedTime() >= other.getSavedTime() && getIdleTime() <= other.getIdleTime()) return 1;
+ if (getSavedTime() <= other.getSavedTime() && getIdleTime() >= other.getIdleTime()) return -1;
+ throw new RuntimeException("comparing pareto metrics");
+ }
+
+ @Override
+ public int hashCode() {
+ int hash = 7;
+ hash = 97 * hash + (int) (this.ttl ^ (this.ttl >>> 32));
+ return hash;
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (!(obj instanceof Metrics)) {
+ return false;
+ }
+ return compareTo((Metrics) obj) == 0;
+ }
+
+ @Override
+ public String toString() {
+ return "TTL: " + this.ttl
+ + " SavedTime: " + this.savedTime
+ + " Hits: " + this.hits
+ + " ComputationTime: " + this.computationTime
+ + " TimeInCache: " + this.timeInCache
+ + " Stales: " + this.stales;
+ }
}
diff --git a/src/main/java/br/ufrgs/inf/prosoft/tfcache/Pareto.java b/src/main/java/br/ufrgs/inf/prosoft/tfcache/Pareto.java
index 50e96cd..1d8fdac 100755
--- a/src/main/java/br/ufrgs/inf/prosoft/tfcache/Pareto.java
+++ b/src/main/java/br/ufrgs/inf/prosoft/tfcache/Pareto.java
@@ -2,6 +2,8 @@ package br.ufrgs.inf.prosoft.tfcache;
import br.ufrgs.inf.prosoft.tfcache.configuration.Configuration;
+import java.math.BigDecimal;
+import java.math.MathContext;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
import java.util.stream.Collectors;
@@ -9,9 +11,9 @@ import java.util.stream.Stream;
public class Pareto {
- private final Map<Double, Metrics> savedTimeHasMetrics;
+ private final Map<Long, Metrics> savedTimeHasMetrics;
private Metrics bestMetrics;
- private Double minEuclideanDistance;
+ private BigDecimal minEuclideanDistance;
public Pareto() {
savedTimeHasMetrics = new ConcurrentHashMap<>();
@@ -28,8 +30,8 @@ public class Pareto {
}
public static void removeDominatedMetrics(Collection<Metrics> allMetrics) {
- Map<Double, List<Metrics>> groupBySavedTime = allMetrics.stream().collect(Collectors.groupingBy(Metrics::getSavedTime));
- groupBySavedTime.remove(0D);
+ Map<Long, List<Metrics>> groupBySavedTime = allMetrics.stream().collect(Collectors.groupingBy(Metrics::getSavedTime));
+ groupBySavedTime.remove(0L);
groupBySavedTime.forEach((savedTime, metrics) -> {
double minIdleTime = metrics.stream().mapToDouble(Metrics::getIdleTime).min().orElse(0);
metrics.removeIf(metric -> metric.getIdleTime() > minIdleTime);
@@ -45,7 +47,6 @@ public class Pareto {
}
public synchronized void addIfPareto(Metrics metrics) {
- if (metrics.getSavedTime() == 0) return;
savedTimeHasMetrics.merge(metrics.getSavedTime(), metrics, (existing, incoming) -> existing.getIdleTime() < incoming.getIdleTime() ? existing : incoming);
}
@@ -57,8 +58,9 @@ public class Pareto {
return values().stream().map(Metrics::getTtl).collect(Collectors.toSet());
}
- public Pareto getNormalised() {
- if (savedTimeHasMetrics.isEmpty()) return this;
+ public BigDecimal getNormalisedMinEuclideanDistance() {
+ if (savedTimeHasMetrics.isEmpty()) throw new RuntimeException("savedTimeHasMetrics is empty");
+
double minSavedTime = values().stream().mapToDouble(Metrics::getSavedTime).min().orElseThrow();
double maxSavedTime = values().stream().mapToDouble(Metrics::getSavedTime).max().orElseThrow();
double distanceSavedTime = maxSavedTime - minSavedTime;
@@ -66,23 +68,22 @@ public class Pareto {
double maxIdleTime = values().stream().mapToDouble(Metrics::getIdleTime).max().orElseThrow();
double distanceIdleTime = maxIdleTime - minIdleTime;
- Stream<Metrics> normalisedPareto = values().stream().map(it -> {
- double normalisedSavedTime = (it.getSavedTime() - minSavedTime) / distanceSavedTime;
- double normalisedIdleTime = (it.getIdleTime() - minIdleTime) / distanceIdleTime;
- return it.getNormalised(normalisedSavedTime, normalisedIdleTime);
- });
- return new Pareto(normalisedPareto);
+ List<BigDecimal> normalisedEuclideanDistances = values().stream().map(it -> {
+ BigDecimal normalisedSavedTime = new BigDecimal(it.getSavedTime() - minSavedTime).divide(BigDecimal.valueOf(distanceSavedTime), MathContext.DECIMAL128);
+ BigDecimal normalisedIdleTime = new BigDecimal(it.getIdleTime() - minIdleTime).divide(BigDecimal.valueOf(distanceIdleTime), MathContext.DECIMAL128);
+ return Metrics.calculateEuclideanDistance(normalisedSavedTime, normalisedIdleTime, Configuration.getPreferences().get(0), Configuration.getPreferences().get(1));
+ }).collect(Collectors.toList());
+ return normalisedEuclideanDistances.stream().min(BigDecimal::compareTo).orElseThrow();
}
- public Double getMinEuclideanDistance() {
- if (minEuclideanDistance == null) getBestMetrics();
+ public BigDecimal getMinEuclideanDistance() {
+ getBestMetrics();
return minEuclideanDistance;
}
public Metrics getBestMetrics() {
- if (this.bestMetrics == null) this.bestMetrics = getBestMetrics(Configuration.getPreferences().get(0), Configuration.getPreferences().get(1));
- this.minEuclideanDistance = this.bestMetrics.calculateEuclideanDistance(Configuration.getPreferences().get(0), Configuration.getPreferences().get(1));
- return this.bestMetrics;
+ if (bestMetrics == null) bestMetrics = getBestMetrics(Configuration.getPreferences().get(0), Configuration.getPreferences().get(1));
+ return bestMetrics;
}
private Metrics getBestMetrics(double percentageObjectiveSavedTime, double percentageObjectiveIdleTime) {
@@ -91,7 +92,9 @@ public class Pareto {
if (savedTimeHasMetrics.isEmpty()) return new Metrics();
double minIdleTime = values().stream().mapToDouble(Metrics::getIdleTime).min().orElseThrow() * percentageObjectiveIdleTime;
double maxSavedTime = values().stream().mapToDouble(Metrics::getSavedTime).max().orElseThrow() * percentageObjectiveSavedTime;
- return values().stream().min(Comparator.comparingDouble(it -> it.calculateEuclideanDistance(maxSavedTime, minIdleTime))).orElseThrow();
+ bestMetrics = values().stream().min(Comparator.comparing(it -> it.calculateEuclideanDistance(maxSavedTime, minIdleTime))).orElseThrow();
+ minEuclideanDistance = bestMetrics.calculateEuclideanDistance(maxSavedTime, minIdleTime);
+ return bestMetrics;
}
}
diff --git a/src/main/java/br/ufrgs/inf/prosoft/tfcache/Simulator.java b/src/main/java/br/ufrgs/inf/prosoft/tfcache/Simulator.java
index 7744b76..447c4a0 100755
--- a/src/main/java/br/ufrgs/inf/prosoft/tfcache/Simulator.java
+++ b/src/main/java/br/ufrgs/inf/prosoft/tfcache/Simulator.java
@@ -54,8 +54,8 @@ public class Simulator {
if (occurrence.getExecutionTime() < 0) throw new RuntimeException("executionTime cannot be under zero");
if (adjustedEndTime < adjustedStartTime) throw new RuntimeException("adjustedEndTime should not be lesser than adjustedStartTime");
- if (inputHasCachedTime.containsKey(occurrence.getParametersSerialised()) &&
- adjustedStartTime - inputHasCachedTime.get(occurrence.getParametersSerialised()) > ttl) {
+ if (inputHasCachedTime.containsKey(occurrence.getParametersSerialised())
+ && adjustedStartTime - inputHasCachedTime.get(occurrence.getParametersSerialised()) > ttl) {
inputHasCachedTime.remove(occurrence.getParametersSerialised());
}
if (inputHasCachedTime.containsKey(occurrence.getParametersSerialised())) {