public async Task <double[]> EvaluateCellsBatchAsync(IEnumerable <ICellRequest> cells) { ICellRequest first = cells.FirstOrDefault(); if (first == null) { return(new double[0]); } else { var cellsArray = cells.ToArray(); ts.TraceEvent(TraceEventType.Start, 3, "Uncertainty evaluation started"); Stopwatch sw = Stopwatch.StartNew(); int N = cellsArray.Length; Task <double>[] resultTasks = new Task <double> [N]; for (int i = 0; i < N; i++) { var cell = cellsArray[i]; var coverage = GetIPsForCell(cell); IPs tempIps = coverage.Item1; var capturedValues = Tuple.Create(coverage.Item2, coverage.Item3, cell); double sd = baseNodeUncertatintyProvider.GetBaseNodeStandardDeviation(cell); resultTasks[i] = temporalVarianceCalculator.GetVarianceForCombinationAsync(tempIps, cell, sd * sd).ContinueWith((t, obj) => //Using continuations to queue all the cells for calculation instead of awaiting for each of them { Tuple <IPs, IPs, ICellRequest> captured = (Tuple <IPs, IPs, ICellRequest>)obj; IPs latIps = captured.Item1, lonIps = captured.Item2; var cell2 = captured.Item3; double temporalVariance = t.Result; return(spatialVarianceCalculator.GetVarianceForCombinationAsync(latIps, lonIps, cell2, temporalVariance).ContinueWith(t2 => { var res = t2.Result; return Math.Sqrt(res); })); }, capturedValues).Unwrap(); } double[] result = await Task.WhenAll(resultTasks); sw.Stop(); ts.TraceEvent(TraceEventType.Stop, 3, string.Format("Calculated uncertainty for {0} cells in {1}", N, sw.Elapsed)); return(result); } }
public async Task <LinearWeight[]> GetLinearWeigthsAsync(ICellRequest cell, TContext interpolationContext) { if (cell.LatMin == cell.LatMax && cell.LonMin == cell.LonMax) { return(await component.GetLinearWeigthsAsync(cell.LatMin, cell.LonMin, interpolationContext)); } else { double latStep = (cell.LatMax - cell.LatMin) / (cellDivisionNum - 1); double lonStep = (cell.LonMax - cell.LonMin) / (cellDivisionNum - 1); Dictionary <int, double> weigthsDict = new Dictionary <int, double>(); for (int i = 0; i < cellDivisionNum; i++) { for (int j = 0; j < cellDivisionNum; j++) { var weights = await component.GetLinearWeigthsAsync(cell.LatMin + i *latStep, cell.LonMin + j *lonStep, interpolationContext); int K = weights.Length; for (int k = 0; k < K; k++) { int idx = weights[k].DataIndex; if (weigthsDict.ContainsKey(idx)) { weigthsDict[idx] += weights[k].Weight; } else { weigthsDict.Add(idx, weights[k].Weight); } } } } double M = cellDivisionNum * cellDivisionNum; var result = weigthsDict.Select(kvp => { return(new LinearWeight(kvp.Key, kvp.Value / M)); }).ToArray(); System.Diagnostics.Debug.Assert(Math.Abs(result.Sum(e => e.Weight) - 1.0) < 1e-6);//test for unbiasness, requires component.GetLinearWeigths to be unbiased return(result); } }
public async Task <double[]> EvaluateCellsBatchAsync(IEnumerable <ICellRequest> cells) { ICellRequest first = cells.FirstOrDefault(); if (first == null) { return(new double[0]); } else { string varName = first.VariableName; if (!storageDef.VariablesDimensions.ContainsKey(varName)) { throw new InvalidOperationException(string.Format("Request to the variable \"{0}\" that is not found in the data storage. Check the variable name mapping in the FetchClimate configuration", varName)); } return(await component.EvaluateCellsBatchAsync(cells)); } }
private DataCoverageResult GetCoverage(ICellRequest cell) { var timeR = timeCoverageProvider.GetCoverage(cell.Time); var latR = latCoverageProvider.GetCoverage(cell.LatMin, cell.LatMax); var lonR = lonCoverageProvider.GetCoverage(cell.LonMin, cell.LonMax); if (timeR == DataCoverageResult.OutOfData || latR == DataCoverageResult.OutOfData || lonR == DataCoverageResult.OutOfData) { return(DataCoverageResult.OutOfData); } else if (timeR == DataCoverageResult.DataWithoutUncertainty || latR == DataCoverageResult.DataWithoutUncertainty || lonR == DataCoverageResult.DataWithoutUncertainty) { return(DataCoverageResult.DataWithoutUncertainty); } else { return(DataCoverageResult.DataWithUncertainty); } }
public async Task <T> GetAsync(ICellRequest nodes) { IGeoCellEquatible ine = nodes as IGeoCellEquatible; if (ine == null) { ine = converter.Covert(nodes); } var lazyResult = cache.GetOrAdd(ine, new AsyncLazy <T>(async() => { T newResult = await component.GetAsync(nodes); return(newResult); })); var result = await lazyResult.GetValueAsync(); return(result); }
public async Task LinearWeightsContextFactoryFacadeTest() { var lwcff = new LinearWeightsContextFactoryFacade <RealValueNodesStub>(new Stub4(), new Stub3()); var cells = new ICellRequest[] { new Stub5() }; var lwc = await lwcff.CreateAsync(cells); var combs = lwc.Combinations.ToArray(); Assert.AreEqual(1, combs.Length); Assert.AreEqual(cells[0], combs[0].Item1); RealValueNodes nodes = combs[0].Item2; IEnumerable <LinearWeight> weights = combs[0].Item3; var result = weights.Sum(w => w.Weight * nodes.Values[w.DataIndex]); Assert.AreEqual(847.0, result); }
public Task <double> GetVarianceForCombinationAsync(IPs temporalWeights, ICellRequest cell, double baseNodeVariance) { var capturedValues = Tuple.Create(temporalWeights, cell, baseNodeVariance); return(Task.Factory.StartNew(obj => { Tuple <IPs, ICellRequest, double> typedObj = (Tuple <IPs, ICellRequest, double>)obj; var name = typedObj.Item2.VariableName; var processDescription = dict.GetOrAdd(name, new Lazy <IGaussianProcessDescription>(() => { var v = variogramFactory.Create(name); if (v == null) { ts.TraceEvent(TraceEventType.Warning, 1, string.Format("Could not find temporal variogram for the \"{0}\" variable. Skipping uncertainty propagation analysis", name)); } else { ts.TraceEvent(TraceEventType.Information, 2, string.Format("Loaded temporal variogram for \"{0}\" variable", name)); } return v; }, System.Threading.LazyThreadSafetyMode.ExecutionAndPublication)).Value; if (processDescription == null) //Variogram not found. { return double.MaxValue; } var variogram = processDescription.Variogram; var tempPrecomputedNugget = variogram.Nugget; var tempPrecomputedSill = variogram.Sill; double tempSpatIndependentVariance = double.IsNaN(typedObj.Item3) ? (tempPrecomputedNugget) : (typedObj.Item3); var tempVarProps = new TemporalVarianceProperties(tempPrecomputedSill - tempPrecomputedNugget + tempSpatIndependentVariance, new Func <double, double, double>((coord1, coord2) => (tempPrecomputedSill - variogram.GetGamma(processDescription.Dist(coord1, coord2))))); double temporalVariance = GetTemporalVariance(typedObj.Item1, timeAxis, axisLocator.getAproximationGrid(cell.Time), tempVarProps); Debug.Assert(temporalVariance >= 0.0); return temporalVariance; }, capturedValues)); }
/// <summary> /// The method producing double array of mean values from the sequence of cells /// </summary> /// <param name="variable">A variable name (data source scope) to get the mean values for</param> /// <param name="cells">A sequence of cells to get the mean values for</param> /// <returns></returns> public async Task <double[]> AggregateCellsBatchAsync(IEnumerable <ICellRequest> cells) { ICellRequest first = cells.FirstOrDefault(); if (first == null) { return(new double[0]); } else { var cellArray = cells.ToArray(); var variable = first.VariableName; DataDomain dataDomain = CalcDataDomain(cellArray, this.timeBBCalc, this.latBBcalc, this.lonBBcalc); if (dataDomain == null) { return(Enumerable.Repeat(double.NaN, cellArray.Length).ToArray()); } Array data = await FetchRawDataAsync(dataStorage, dataDomain, variable); double[] result = arrayAggregator.Aggregate(variable, data, dataDomain, cellArray).ToArray(); return(result); } }
public SuffixCell(string suffix, ICellRequest cell) { _suffix = suffix; _cell = cell; }
public async Task <RealValueNodes> GetAsync(ICellRequest cell) { var variableName = cell.VariableName; var timeSegment = cell.Time; var bounds = timeIntegrator.GetBoundingBox(timeSegment); if (bounds.IsSingular) { double[] empty = new double[0]; return(new RealValueNodes(empty, empty, empty)); } int[] origin = new int[2]; int[] shape = new int[2]; int timeDimNum = timeDimNumber[variableName]; int stationDimNum = stationsDimNumber[variableName]; int[] stationsIdxs = stationLocator.GetRelevantStationsIndices(cell); int stationMinIdx = stationsIdxs.Min(), stationMaxIdx = stationsIdxs.Max(); int stationsCount = stationsIdxs.Length; //data fetching origin[timeDimNum] = bounds.first; origin[stationDimNum] = stationMinIdx; shape[timeDimNum] = bounds.last - bounds.first + 1; shape[stationDimNum] = stationMaxIdx - stationMinIdx + 1; traceSource.TraceEvent(TraceEventType.Verbose, 2, "Requesting raw data for cell"); var dataTask = dataStorage.GetDataAsync(variableName, origin, null, shape); //integration points calculation IPs timeIntegrationPoints = timeIntegrator.GetTempIPs(timeSegment); IPs[][] ips = new IPs[stationsCount][]; for (int i = 0; i < stationsCount; i++) { var curr = new IPs[2]; ips[i] = curr; int idx = stationsIdxs[i]; curr[stationDimNum] = new IPs() { Weights = new double[] { 1.0 }, Indices = new int[] { idx }, BoundingIndices = new IndexBoundingBox() { first = idx, last = idx } }; curr[timeDimNum] = timeIntegrationPoints; } var data = await dataTask; object missingValue = missingValuesDict.GetMissingValue(variableName); if (missingValue != null && missingValue.GetType() != varTypes[variableName]) { traceSource.TraceEvent(TraceEventType.Warning, 1, string.Format("A missing value of the variable \"{0}\"has different type from variable type. Ignoring MV definition", variableName)); missingValue = null; } IEnumerable <Utils.IntegrationResult> obsResults; if (missingValue != null) { obsResults = Utils.ArrayMean.IntegrateSequenceWithMVs2D(variableName, data, missingValue, origin, ips); } else { obsResults = Utils.ArrayMean.IntegrateSequence2D(variableName, data, origin, ips); } double scaleFacotor = dataRepresentationDictionary.ScaleFactors[variableName]; double addOffset = dataRepresentationDictionary.AddOffsets[variableName]; var scaledResults = obsResults.Select(r => (r.Integral / r.SumOfWeights) * scaleFacotor + addOffset).ToArray(); int len = scaledResults.Length; List <double> valuesList = new List <double>(len); List <double> latsList = new List <double>(len); List <double> lonsList = new List <double>(len); for (int i = 0; i < len; i++) { if (!double.IsNaN(scaledResults[i])) { valuesList.Add(scaledResults[i]); latsList.Add(stationsLats[stationsIdxs[i]]); lonsList.Add(stationsLons[stationsIdxs[i]]); } } return(new RealValueNodes(latsList.ToArray(), lonsList.ToArray(), valuesList.ToArray())); }
public Task <double> GetVarianceForCombinationAsync(IPs latWeights, IPs lonWeights, ICellRequest cell, double baseNodeVariance) { Tuple <IPs, IPs, ICellRequest, double> capturedValues = Tuple.Create(latWeights, lonWeights, cell, baseNodeVariance); return(Task.Factory.StartNew(obj => { Tuple <IPs, IPs, ICellRequest, double> arg = (Tuple <IPs, IPs, ICellRequest, double>)obj; var cell2 = arg.Item3; var name = cell2.VariableName; double[] targetLats, targetLons; if (cell2.LatMax == cell2.LatMin && cell2.LonMax == cell2.LonMin) { targetLats = new double[] { cell2.LatMax }; targetLons = new double[] { cell2.LonMax }; } else { double latStep = (cell2.LatMax - cell2.LatMin) / (cellDevisionCount - 1); double lonStep = (cell2.LonMax - cell2.LonMin) / (cellDevisionCount - 1); targetLats = Enumerable.Range(0, cellDevisionCount).Select(j => cell2.LatMin + j * latStep).ToArray(); targetLons = Enumerable.Range(0, cellDevisionCount).Select(j => cell2.LonMin + j * lonStep).ToArray(); } //coerce each target location to the closest data grid node. As closest data grid node is representative for its region. (indirect coercing of distance function by moving target locations) targetLats = Align(latAxis, targetLats); targetLons = Align(lonAxis, targetLons); var fieldDescription = dict.GetOrAdd(name, new Lazy <IGaussianFieldDescription>(() => { var v = variogramsFactory.Create(name); if (v == null) { ts.TraceEvent(TraceEventType.Warning, 1, string.Format("Could not find spatial variogram for the \"{0}\" variable. Skipping uncertainty propagation analysis", name)); } else { ts.TraceEvent(TraceEventType.Information, 2, string.Format("Loaded spatial variogram for \"{0}\" variable", name)); } return v; }, System.Threading.LazyThreadSafetyMode.ExecutionAndPublication)).Value; if (fieldDescription == null) { return double.MaxValue; } var variogram = fieldDescription.Variogram; var spatPrecomputedSill = variogram.Sill; var spatPrecomputedNugget = variogram.Nugget; var coercedBaseVariance = double.IsNaN(arg.Item4) ? (spatPrecomputedNugget) : arg.Item4; var spatDistance = new Func <double, double, double, double, double>((lat1, lon1, lat2, lon2) => fieldDescription.Dist(lat1, lon1, lat2, lon2)); var spatCovariogram = new Func <double, double>(distance => (spatPrecomputedSill - variogram.GetGamma(distance))); SpatialVarianceProperties svp = new SpatialVarianceProperties(spatPrecomputedSill - spatPrecomputedNugget + coercedBaseVariance, spatDistance, spatCovariogram); return GetSpatialVariance(arg.Item1, arg.Item2, latAxis, lonAxis, targetLats, targetLons, svp); //basic scale_factor/add_offset data transform are assumed to be applied during variograms fitting }, capturedValues)); }
public async Task <double[]> EvaluateCellsBatchAsync(IEnumerable <ICellRequest> cells) { ICellRequest[] cellArray = cells.ToArray(); int N = cellArray.Length; if (N == 0) { return(new double[0]); } else { bool[] passToComponentFlags = new bool[N]; bool[] fullCoverageFlags = new bool[N]; double[] result = new double[N]; List <ICellRequest> passToComponentCells = new List <ICellRequest>(N); //Result matrix //Integrators info\non-MV concentration 0.0 (0.0;1.0) 1.0 //With unc ND NU U //Without unc ND NU NU //Out of range (no mean values) ND ND ND for (int i = 0; i < N; i++) { ICellRequest cell = cellArray[i]; double landP = maskProvider.GetDataPercentage(cell.LatMin, cell.LatMax, cell.LonMin, cell.LonMax); bool passToComponentFlag = true; bool fullCoverageFlag = false; if (landP == 0.0) { passToComponentFlag = false; result[i] = double.NaN; } else if (landP == 1.0) { fullCoverageFlag = true; } passToComponentFlags[i] = passToComponentFlag; fullCoverageFlags[i] = fullCoverageFlag; if (passToComponentFlag) { passToComponentCells.Add(cell); } } double[] componentResults = await component.EvaluateCellsBatchAsync(passToComponentCells); int pointer = 0; for (int i = 0; i < N; i++) { if (passToComponentFlags[i]) { if (!double.IsNaN(componentResults[pointer]) && !fullCoverageFlags[i]) { result[i] = double.MaxValue; } else { result[i] = componentResults[pointer]; } pointer++; } } return(result); } }
public double GetBaseNodeStandardDeviation(ICellRequest cell) { return(double.NaN); }
public async Task <LinearWeight[]> GetLinearWeigthsAsync(INodes nodes, ICellRequest cell) { TContext context = await contextProvider.GetAsync(nodes); return(await weightsProvider.GetLinearWeigthsAsync(cell, context)); }
public async Task <RealValueNodesStub> GetAsync(ICellRequest cell) { return(new RealValueNodesStub()); }
public async Task <double> GetVarianceForCombinationAsync(IPs temporalWeights, ICellRequest cell, double baseVariance) { return(baseVariance); }