91 lines
3.4 KiB
C#
91 lines
3.4 KiB
C#
///
|
|
/// Copyright (c) 2013-2022 Sensus Slovensko a.s.
|
|
///
|
|
using System;
|
|
using System.Collections.Generic;
|
|
|
|
namespace Config.Entities
|
|
{
|
|
public class MeasurementCorrection : Common.IMeasurementCorrection, IComparable<MeasurementCorrection>
|
|
{
|
|
public virtual int Id { get; protected set; }
|
|
public virtual int RangeIx { get; set; } /// 0..5
|
|
public virtual double Measurement { get; set; }
|
|
public virtual double Correction { get; set; }
|
|
|
|
public MeasurementCorrection()
|
|
{
|
|
RangeIx = 0;
|
|
}
|
|
|
|
public MeasurementCorrection(int rangeIx)
|
|
{
|
|
RangeIx = rangeIx;
|
|
}
|
|
|
|
public virtual int CompareTo(MeasurementCorrection other)
|
|
{
|
|
return (Measurement > other.Measurement) ? 1 : ((Measurement == other.Measurement) ? 0 : -1);
|
|
}
|
|
|
|
|
|
/// <summary>
|
|
/// Calculates corrected value from a list of corrections by interpolation.
|
|
/// It is assumed that values in the list 'corrections' are sorted.
|
|
/// </summary>
|
|
/// <param name="rawMeasurement">Raw uncorrected value</param>
|
|
/// <param name="corrections">Sorted (value, correction) pairs</param>
|
|
/// <returns>Corrected value</returns>
|
|
public static double CorrectedValue(double rawValue, IList<MeasurementCorrection> corrections)
|
|
{
|
|
return rawValue + GetCorrection(rawValue, corrections);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Get a correction from a list of corrections by interpolation.
|
|
/// It is assumed that values in the list 'corrections' are sorted.
|
|
/// </summary>
|
|
/// <param name="rawMeasurement">Raw uncorrected value</param>
|
|
/// <param name="corrections">Sorted (value, correction) pairs</param>
|
|
/// <returns>Corrected value</returns>
|
|
public static double GetCorrection(double rawValue, IList<MeasurementCorrection> corrections)
|
|
{
|
|
if ((corrections == null) || (corrections.Count == 0)) return 0; /// No correction
|
|
|
|
if (rawValue < corrections[0].Measurement)
|
|
{
|
|
/// rawValue is below the lowest value in the correction table
|
|
return corrections[0].Correction;
|
|
}
|
|
|
|
for (int i = 1; i < corrections.Count; i++)
|
|
{
|
|
if (rawValue < corrections[i].Measurement)
|
|
{
|
|
double d1 = rawValue - corrections[i - 1].Measurement;
|
|
double d2 = corrections[i].Measurement - rawValue;
|
|
|
|
if (d1 + d2 <= float.Epsilon)
|
|
{
|
|
/// Neigboring values in the corection table are close to each other -> calculate the average
|
|
return (corrections[i - 1].Correction + corrections[i].Correction) / 2.0;
|
|
}
|
|
else
|
|
{
|
|
/// Interpolate the correction from neigboring values in the corection table
|
|
return (corrections[i - 1].Correction * d2 + corrections[i].Correction * d1) / (d1 + d2);
|
|
}
|
|
}
|
|
}
|
|
|
|
/// rawValue is above the highest value in the correction table
|
|
return corrections[corrections.Count - 1].Correction;
|
|
}
|
|
|
|
public override string ToString()
|
|
{
|
|
return string.Format("{0} {1} ({2})", Measurement, Correction, RangeIx);
|
|
}
|
|
}
|
|
}
|