Add measurements_analysis/src/measurements_analysis/core.py

This commit is contained in:
Mika 2025-12-14 16:47:08 +00:00
commit 75e4788dc3

View file

@ -0,0 +1,67 @@
from dataclasses import dataclass
from typing import List, Dict
import statistics
from scipy.stats import levene
@dataclass
class MeasurementData:
spacing_mm: float
hf_amplitude: float
spike_outlier_rate: float
levenes_test_p: float
def analyze_measurements(data: List[MeasurementData]) -> Dict[float, Dict[str, float]]:
"""Analysiert HF-Messdaten und berechnet Kennzahlen pro Abstand.
Args:
data: Liste von MeasurementData-Objekten.
Returns:
Dictionary mit Abstand als Schlüssel und statistischen Kennzahlen
(Mittelwert, Varianz, Ausreißer-Rate, p-Wert) als Wert.
"""
if not data:
return {}
# Gruppiere nach spacing_mm
grouped = {}
for d in data:
if not isinstance(d, MeasurementData):
raise TypeError("Each item must be a MeasurementData instance.")
grouped.setdefault(d.spacing_mm, []).append(d)
results = {}
all_amplitude_groups = [
[m.hf_amplitude for m in measurements]
for measurements in grouped.values()
]
for spacing, measurements in grouped.items():
amplitudes = [m.hf_amplitude for m in measurements]
outliers = [m.spike_outlier_rate for m in measurements]
pre_pvals = [m.levenes_test_p for m in measurements]
mean_amp = statistics.mean(amplitudes)
var_amp = statistics.variance(amplitudes) if len(amplitudes) > 1 else 0.0
mean_outlier = statistics.mean(outliers)
pre_mean_p = statistics.mean(pre_pvals)
# Berechne Levene-Test über alle Gruppen, wenn sinnvoll
try:
if len(all_amplitude_groups) > 1:
p_val = levene(*all_amplitude_groups).pvalue
else:
p_val = pre_mean_p
except Exception:
p_val = pre_mean_p
results[spacing] = {
"mean_amplitude": mean_amp,
"variance_amplitude": var_amp,
"mean_outlier_rate": mean_outlier,
"levene_p": p_val,
}
return results