evaluate static method
计算综合得分 / Computes the composite score.
所有指标均可选,缺失的指标不参与加权 / Every metric is optional; missing metrics are excluded from the weighted average.
Implementation
static NetworkQualityScore evaluate({
double? latency,
double? jitter,
double? packetLoss,
double? download,
double? upload,
double? dns,
int? signalStrength,
QualityTargets targets = const QualityTargets(),
DateTime? timestamp,
}) {
final targetsSet = targets;
final subScores = <String, double>{};
final raw = <String, double>{};
if (latency != null) {
subScores['latency'] = _lowerIsBetter(
latency,
excellent: targetsSet.excellentLatency,
acceptable: targetsSet.acceptableLatency,
);
raw['latency'] = latency;
}
if (jitter != null) {
subScores['jitter'] = _lowerIsBetter(
jitter,
excellent: targetsSet.excellentJitter,
acceptable: targetsSet.acceptableJitter,
);
raw['jitter'] = jitter;
}
if (packetLoss != null) {
subScores['packetLoss'] = _lowerIsBetter(
packetLoss,
excellent: 0,
acceptable: targetsSet.acceptablePacketLoss,
);
raw['packetLoss'] = packetLoss;
}
if (download != null) {
subScores['download'] = _higherIsBetter(
download,
acceptable: targetsSet.acceptableDownload,
excellent: targetsSet.excellentDownload,
);
raw['download'] = download;
}
if (upload != null) {
subScores['upload'] = _higherIsBetter(
upload,
acceptable: targetsSet.acceptableUpload,
excellent: targetsSet.excellentUpload,
);
raw['upload'] = upload;
}
if (dns != null) {
subScores['dns'] = _lowerIsBetter(
dns,
excellent: targetsSet.excellentDns,
acceptable: targetsSet.acceptableDns,
);
raw['dns'] = dns;
}
if (signalStrength != null) {
subScores['signalStrength'] = _higherIsBetter(
signalStrength.toDouble(),
acceptable: -88,
excellent: -50,
);
raw['signalStrength'] = signalStrength.toDouble();
}
if (subScores.isEmpty) {
return NetworkQualityScore(
score: 0,
level: NetworkQualityLevel.unknown,
metrics: const <String, double>{},
suggestions: const <String>[
'Run a diagnostic first to collect metrics',
],
timestamp: timestamp ?? DateTime.now(),
);
}
var weightedSum = 0.0;
var weightSum = 0.0;
subScores.forEach((metric, value) {
final weight = _weights[metric] ?? 0;
weightedSum += value * weight;
weightSum += weight;
});
final score = weightSum == 0 ? 0.0 : weightedSum / weightSum;
final metrics = <String, double>{...raw};
subScores.forEach((metric, value) {
metrics['subScore.$metric'] = value;
});
return NetworkQualityScore(
score: double.parse(score.toStringAsFixed(2)),
level: NetworkQualityLevel.fromScore(score),
metrics: metrics,
suggestions: _suggestions(subScores, targetsSet),
timestamp: timestamp ?? DateTime.now(),
);
}