public void TestRMSEMassBalance() { SQLiteServer pDB = new SQLiteServer(path); TimeSeriesDatabase DB = new TimeSeriesDatabase(pDB, false); // Reads input data required by the calculation Series daily = DB.GetSeriesFromName("CHEI_QD"); Series monthly = DB.GetSeriesFromName("CHEI_QM"); daily.Read(); monthly.Read(); // disaggregated daily summed to monthly acre-feet Series infilled = Disaggregation.RMSEInterp(daily, monthly); Series infilledMonthlySumAcreFeet = Math.MonthlySum(infilled) * 1.98347; infilledMonthlySumAcreFeet.TimeInterval = TimeInterval.Monthly; // get equal time period for infilled data to original monthly data Series s = infilledMonthlySumAcreFeet.Subset(monthly.MinDateTime, monthly.MaxDateTime); var diff = System.Math.Abs(Math.Sum(monthly - s)); Assert.IsTrue(diff < 0.01, "UofI RMSEInterp mass balance failed by: " + diff); }
/// <summary> /// Merges the disaggregated series with the observed daily series and scales the disaggregated values /// to maintain mass balance. /// </summary> /// <param name="observed"></param> /// <param name="estimated"></param> /// <returns></returns> internal static void MergeCheckMassBalance(Series observed, Series estimated) { // Merge the observed and disaggregated series Series merged = Math.Merge(observed, estimated); // Get monthly sums from the original disaggregated and merged series along with their difference Series disaggMonthlyVol = Math.MonthlySum(estimated); Series mergedMonthlyVol = Math.MonthlySum(merged); Series diffVol = disaggMonthlyVol - mergedMonthlyVol; diffVol = TimeSeries.Math.FillMissingWithZero(diffVol); // Adjust estimated values to maintain mass balance foreach (var item in merged) { if (item.Flag == PointFlag.Computed) //handles calculated points { // Get the monthly MB error double mbError = diffVol.Lookup(new DateTime(item.DateTime.Year, item.DateTime.Month, 1)); // Gets the count of calculated points for the month Series sEstCount = merged.Subset(string.Format("{0} >= '{1}' AND {2} <= '{3}' AND {4} = {5}", "[datetime]", new DateTime(item.DateTime.Year, item.DateTime.Month, 1), "[datetime]", new DateTime(item.DateTime.Year, item.DateTime.Month, DateTime.DaysInMonth(item.DateTime.Year, item.DateTime.Month)), "[flag]", "'" + PointFlag.Computed + "'")); int estCount = sEstCount.Count; if (mbError != 0.0 && estCount > 0) //MB error, adjust calculated points { Point p = estimated[item.DateTime]; double mbAdjust = mbError / estCount; p.Value = item.Value + mbAdjust; estimated[item.DateTime] = p; } } else if (estimated.IndexOf(item.DateTime) < 0) { //add observed data to estimated estimated.Add(merged[item.DateTime]); } else { //replace estimated data with observed estimated[item.DateTime] = merged[item.DateTime]; } } }