Skip to content

Commit 89523ff

Browse files
committed
Implement Plottable interface in ValidTSCInstancesPerProjectionMetric
1 parent b9c4ae4 commit 89523ff

File tree

1 file changed

+99
-3
lines changed

1 file changed

+99
-3
lines changed

stars-core/src/main/kotlin/tools/aqua/stars/core/metric/metrics/evaluation/ValidTSCInstancesPerProjectionMetric.kt

Lines changed: 99 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,10 @@
1818
package tools.aqua.stars.core.metric.metrics.evaluation
1919

2020
import java.util.logging.Logger
21+
import tools.aqua.stars.core.metric.metrics.utils.getNTimes
22+
import tools.aqua.stars.core.metric.metrics.utils.plotDataAsLineChart
2123
import tools.aqua.stars.core.metric.providers.Loggable
24+
import tools.aqua.stars.core.metric.providers.Plottable
2225
import tools.aqua.stars.core.metric.providers.ProjectionAndTSCInstanceNodeMetricProvider
2326
import tools.aqua.stars.core.metric.providers.Stateful
2427
import tools.aqua.stars.core.tsc.TSCInstance
@@ -28,14 +31,16 @@ import tools.aqua.stars.core.types.EntityType
2831
import tools.aqua.stars.core.types.SegmentType
2932
import tools.aqua.stars.core.types.TickDataType
3033

34+
const val VALID_TSC_INSTANCES_PER_PROJECTION_METRIC_NAME = "valid-tsc-instances-per-projection"
35+
3136
/**
3237
* This class implements the [ProjectionAndTSCInstanceNodeMetricProvider] and tracks the occurred
3338
* valid [TSCInstance] for each [TSCProjection].
3439
*/
3540
class ValidTSCInstancesPerProjectionMetric<
3641
E : EntityType<E, T, S>, T : TickDataType<E, T, S>, S : SegmentType<E, T, S>>(
37-
override val logger: Logger = Loggable.getLogger("valid-tsc-instances-per-projection")
38-
) : ProjectionAndTSCInstanceNodeMetricProvider<E, T, S>, Stateful, Loggable {
42+
override val logger: Logger = Loggable.getLogger(VALID_TSC_INSTANCES_PER_PROJECTION_METRIC_NAME)
43+
) : ProjectionAndTSCInstanceNodeMetricProvider<E, T, S>, Stateful, Loggable, Plottable {
3944
/**
4045
* Map a [TSCProjection] to a map in which the occurrences of valid [TSCInstanceNode]s are stored:
4146
* Map<projection,Map<referenceInstance,List<TSCInstance>>>
@@ -46,6 +51,13 @@ class ValidTSCInstancesPerProjectionMetric<
4651
MutableMap<TSCInstanceNode<E, T, S>, MutableList<TSCInstance<E, T, S>>>> =
4752
mutableMapOf()
4853

54+
/**
55+
* Map a [TSCProjection] to a list of increasing counts of occurrences of valid [TSCInstanceNode]
56+
* s. Map<projection,List<increasing count>>
57+
*/
58+
private val uniqueTimedInstances: MutableMap<TSCProjection<E, T, S>, MutableList<Int>> =
59+
mutableMapOf()
60+
4961
/**
5062
* Track the valid [TSCInstance]s for each [TSCProjection] in the [validInstancesMap]. If the
5163
* current [tscInstance] is invalid it is skipped.
@@ -55,11 +67,19 @@ class ValidTSCInstancesPerProjectionMetric<
5567
*/
5668
override fun evaluate(projection: TSCProjection<E, T, S>, tscInstance: TSCInstance<E, T, S>) {
5769
validInstancesMap.putIfAbsent(projection, mutableMapOf())
70+
// Get current count of unique and valid TSC instance for the current projection
71+
val projectionValidInstances = validInstancesMap.getValue(projection)
72+
73+
// Track current TSC instance even if it is not valid
74+
uniqueTimedInstances.putIfAbsent(projection, mutableListOf())
75+
val projectionValidInstancesCount = uniqueTimedInstances.getValue(projection)
76+
// Add current count of observed instances to list of timed instance counts
77+
projectionValidInstancesCount.add(projectionValidInstances.size)
78+
5879
// Check if given tscInstance is valid
5980
if (!projection.possibleTSCInstances.contains(tscInstance.rootNode)) {
6081
return
6182
}
62-
val projectionValidInstances = validInstancesMap.getValue(projection)
6383
projectionValidInstances.putIfAbsent(tscInstance.rootNode, mutableListOf())
6484
// Get already observed instances for current projection
6585
val projectionValidInstanceList = projectionValidInstances.getValue(tscInstance.rootNode)
@@ -96,4 +116,80 @@ class ValidTSCInstancesPerProjectionMetric<
96116
}
97117
}
98118
}
119+
120+
override fun plotData() {
121+
val xAxisName = "unique and valid TSC instances"
122+
val yAxisName = "instance count"
123+
val yAxisNamePercentage = "$yAxisName (in %)"
124+
val plotFileName = "validTSCInstancesPerProjection"
125+
126+
val combinedXValues = mutableListOf<Int>()
127+
val combinedYValues = mutableListOf<Int>()
128+
val combinedYPercentageValues = mutableListOf<Float>()
129+
val combinedLegendEntries = mutableListOf<String>()
130+
131+
uniqueTimedInstances.keys.forEach { projection ->
132+
// Get list of timed instances for current projection. If not existing: return
133+
val projectionTimedInstances = uniqueTimedInstances[projection] ?: return@forEach
134+
val xValues: List<Int> = List(projectionTimedInstances.size) { it }
135+
val possibleTscInstancesForProjection = projection.possibleTSCInstances.size
136+
val lastYValue = projectionTimedInstances.last()
137+
val legendEntries: List<String> =
138+
getNTimes(
139+
"${projection.id} ($lastYValue/$possibleTscInstancesForProjection)", xValues.size)
140+
141+
// Plot the timed absolute count of unique TSC instances for the current projection
142+
plotDataAsLineChart(
143+
xValues = xValues,
144+
xAxisName = xAxisName,
145+
yValues = projectionTimedInstances,
146+
yAxisName = yAxisName,
147+
legendEntries = legendEntries,
148+
legendHeader = "Projection",
149+
metricName = VALID_TSC_INSTANCES_PER_PROJECTION_METRIC_NAME,
150+
plotFileName = "${plotFileName}_${projection.id}",
151+
plotFileSubFolder = projection.id.toString())
152+
153+
// Plot the timed percentage count of unique TSC instances for the current projection
154+
val yValuesPercentage: List<Float> =
155+
projectionTimedInstances.map { (it.toFloat() / possibleTscInstancesForProjection) * 100 }
156+
plotDataAsLineChart(
157+
xValues = xValues,
158+
xAxisName = xAxisName,
159+
yValues = yValuesPercentage,
160+
yAxisName = yAxisNamePercentage,
161+
legendEntries = legendEntries,
162+
legendHeader = "Projection",
163+
metricName = VALID_TSC_INSTANCES_PER_PROJECTION_METRIC_NAME,
164+
plotFileName = "${plotFileName}_${projection.id}_percentages",
165+
plotFileSubFolder = projection.id.toString())
166+
167+
combinedXValues += xValues
168+
combinedYValues += projectionTimedInstances
169+
combinedLegendEntries += legendEntries
170+
combinedYPercentageValues += yValuesPercentage
171+
}
172+
173+
// Plot the timed absolute count of unique TSC instances for all projections combined
174+
plotDataAsLineChart(
175+
xValues = combinedXValues,
176+
xAxisName = xAxisName,
177+
yValues = combinedYValues,
178+
yAxisName = yAxisName,
179+
legendEntries = combinedLegendEntries,
180+
legendHeader = "Projection",
181+
metricName = VALID_TSC_INSTANCES_PER_PROJECTION_METRIC_NAME,
182+
plotFileName = "${plotFileName}_combined")
183+
184+
// Plot the timed percentage count of unique TSC instances for all projections combined
185+
plotDataAsLineChart(
186+
xValues = combinedXValues,
187+
xAxisName = xAxisName,
188+
yValues = combinedYPercentageValues,
189+
yAxisName = yAxisNamePercentage,
190+
legendEntries = combinedLegendEntries,
191+
legendHeader = "Projection",
192+
metricName = VALID_TSC_INSTANCES_PER_PROJECTION_METRIC_NAME,
193+
plotFileName = "${plotFileName}_combined_percentage")
194+
}
99195
}

0 commit comments

Comments
 (0)