/// <summary> /// Determines the best good point before the end bound. /// </summary> protected void UpdatePriorPoint(BoundingValue bound, AggregateState state) { if (state.HasTerminated && (state.LatePoint == null) && bound.PriorPoint == null) { bound.PriorPoint = state.PriorPoint; bound.PriorBadPoints = state.PriorBadPoints; bound.DerivationType = UseSlopedExtrapolation ? BoundingValueType.SlopedExtrapolation : BoundingValueType.SteppedExtrapolation; } }
/// <summary> /// Returns true if more data is required for the next interval. /// </summary> public override bool WaitForMoreData(TimeSlice bucket, AggregateState state) { bool wait = false; if (!state.HasTerminated) { if (bucket.ContainsTime(state.LatestTimestamp)) { wait = true; } } return(wait); }
/// <summary> /// Updates the value for the time slice. /// </summary> public override DataValue Compute(IAggregationContext context, TimeSlice bucket, AggregateState state) { DataValue retval = new DataValue { SourceTimestamp = bucket.From }; StatusCode code = StatusCodes.BadNoData; DataValue boundValue = context.IsReverseAggregation ? bucket.LateBound.Value : bucket.EarlyBound.Value; if (boundValue != null) { code = bucket.EarlyBound.Value.StatusCode.Code; code.AggregateBits = bucket.EarlyBound.Value.StatusCode.AggregateBits; retval.Value = Convert.ToDouble(bucket.EarlyBound.Value.Value, CultureInfo.InvariantCulture); } if (bucket.Incomplete) code.AggregateBits |= AggregateBits.Partial; retval.StatusCode = code; return retval; }
/// <summary> /// Computes the aggregate value for the time slice. /// </summary> public abstract DataValue Compute(IAggregationContext context, TimeSlice bucket, AggregateState state);
/// <summary> /// Updates the bounding values for the time slice. /// </summary> public override void UpdateBoundingValues(TimeSlice bucket, AggregateState state) { var EarlyBound = bucket.EarlyBound; var LateBound = bucket.LateBound; if (bucket.ExactMatch(state.LatestTimestamp)) { EarlyBound.RawPoint = state.LatePoint ?? state.EarlyPoint; EarlyBound.DerivationType = BoundingValueType.QualityRaw; } else { if (EarlyBound.DerivationType != BoundingValueType.QualityRaw) { if (EarlyBound.EarlyPoint == null) { if ((state.EarlyPoint != null) && (state.EarlyPoint.SourceTimestamp < bucket.From)) { EarlyBound.EarlyPoint = state.EarlyPoint; } } if (EarlyBound.LatePoint == null) { if ((state.LatePoint != null) && (state.LatePoint.SourceTimestamp >= bucket.From)) { EarlyBound.CurrentBadPoints = new List <DataValue>(); foreach (var dv in state.CurrentBadPoints) { if (dv.SourceTimestamp < EarlyBound.Timestamp) { EarlyBound.CurrentBadPoints.Add(dv); } } EarlyBound.DerivationType = BoundingValueType.QualityInterpolation; } } } if (state.HasTerminated && (state.LatePoint == null)) { EarlyBound.CurrentBadPoints = new List <DataValue>(); foreach (var dv in state.CurrentBadPoints) { if (dv.SourceTimestamp < EarlyBound.Timestamp) { EarlyBound.CurrentBadPoints.Add(dv); } } EarlyBound.DerivationType = BoundingValueType.QualityExtrapolation; } } if (bucket.EndMatch(state.LatestTimestamp)) { LateBound.RawPoint = state.LatePoint ?? state.EarlyPoint; LateBound.DerivationType = BoundingValueType.QualityRaw; } else { if (LateBound.DerivationType != BoundingValueType.QualityRaw) { if ((state.EarlyPoint != null) && (state.EarlyPoint.SourceTimestamp < bucket.To)) { LateBound.EarlyPoint = state.EarlyPoint; } if (LateBound.LatePoint == null) { if ((state.LatePoint != null) && (state.LatePoint.SourceTimestamp >= bucket.To)) { LateBound.CurrentBadPoints = new List <DataValue>(); foreach (var dv in state.CurrentBadPoints) { if (dv.SourceTimestamp < LateBound.Timestamp) { LateBound.CurrentBadPoints.Add(dv); } } LateBound.DerivationType = BoundingValueType.QualityInterpolation; } } } if (state.HasTerminated && (state.LatePoint == null)) { LateBound.CurrentBadPoints = new List <DataValue>(); foreach (var dv in state.CurrentBadPoints) { if (dv.SourceTimestamp < LateBound.Timestamp) { LateBound.CurrentBadPoints.Add(dv); } } LateBound.DerivationType = BoundingValueType.QualityExtrapolation; } } }
/// <summary> /// Calculates the value for the time slice. /// </summary> public override DataValue Compute(IAggregationContext context, TimeSlice bucket, AggregateState state) { DataValue retval = new DataValue { SourceTimestamp = bucket.From }; ; StatusCode code = StatusCodes.Good; DataValue previous = new DataValue { SourceTimestamp = bucket.From }; if (bucket.EarlyBound.Value != null) previous.StatusCode = (StatusCode)bucket.EarlyBound.Value.WrappedValue.Value; else previous.StatusCode = StatusCodes.Bad; if (!RightStatusCode(previous)) previous = null; double total = 0.0; foreach (DataValue v in bucket.Values) { if (previous != null) total += (v.SourceTimestamp - previous.SourceTimestamp).TotalMilliseconds; if (RightStatusCode(v)) previous = v; else previous = null; } if (previous != null) total += (bucket.To - previous.SourceTimestamp).TotalMilliseconds; retval.Value = total; code.AggregateBits = AggregateBits.Calculated; if (bucket.Incomplete) code.AggregateBits |= AggregateBits.Partial; retval.StatusCode = code; return retval; }
/// <summary> /// Updates the bounding values for the time slice. /// </summary> public override void UpdateBoundingValues(TimeSlice bucket, AggregateState state) { }
/// <summary> /// Initializes the aggregation. /// </summary> private void InitializeAggregation() { m_state = new AggregateState(this, this); }
/// <summary> /// Updates the data processed by the aggregator. /// </summary> public void UpdateProcessedData(DataValue rawValue, AggregateState state) { // step 1: compute new TimeSlice instances to enqueue, until we reach the one the // rawValue belongs in or we've reached the one that goes to the EndTime. Ensure // that the raw value is added to the last one created. TimeSlice tmpTS = null; if (_pending == null) { _pending = new Queue <TimeSlice>(); } if (_latest == null) { tmpTS = TimeSlice.CreateInitial(StartTime, EndTime, ProcessingInterval); if (tmpTS != null) { _pending.Enqueue(tmpTS); _latest = tmpTS; } } else { tmpTS = _latest; } var latestTime = (StartTime > EndTime) ? StartTime : EndTime; while ((tmpTS != null) && (state.HasTerminated || !tmpTS.AcceptValue(rawValue))) { tmpTS = TimeSlice.CreateNext(latestTime, ProcessingInterval, tmpTS); if (tmpTS != null) { _pending.Enqueue(tmpTS); _latest = tmpTS; } } // step 2: apply the aggregator to the head of the queue to see if we can convert // it into a processed point. If so, dequeue it and add the processed value to the // _released list. Keep doing it until one of the TimeSlices returns null or we // run out of enqueued TimeSlices (should only happen on termination). if (_released == null) { _released = new List <DataValue>(); } foreach (var b in _pending) { UpdateBoundingValues(b, state); } var active = true; while ((_pending.Count > 0) && active) { var top = _pending.Peek(); DataValue computed = null; if (!WaitForMoreData(top, state)) { computed = Compute(this, top, state); } if (computed != null) { _released.Add(computed); _pending.Dequeue(); } else { active = false; } } }
/// <summary> /// Updates the bounding values for the time slice. /// </summary> public override void UpdateBoundingValues(TimeSlice bucket, AggregateState state) { BoundingValue EarlyBound = bucket.EarlyBound; BoundingValue LateBound = bucket.LateBound; if (bucket.ExactMatch(state.LatestTimestamp) && StatusCode.IsGood(state.LatestStatus)) { EarlyBound.RawPoint = state.LatePoint == null ? state.EarlyPoint : state.LatePoint; EarlyBound.DerivationType = BoundingValueType.Raw; } else { if (EarlyBound.DerivationType != BoundingValueType.Raw) { if (EarlyBound.EarlyPoint == null) { if ((state.EarlyPoint != null) && (state.EarlyPoint.SourceTimestamp < bucket.From)) { EarlyBound.EarlyPoint = state.EarlyPoint; } } if (EarlyBound.LatePoint == null) { if ((state.LatePoint != null) && (state.LatePoint.SourceTimestamp >= bucket.From)) { EarlyBound.CurrentBadPoints = new List <DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) { if (dv.SourceTimestamp < EarlyBound.Timestamp) { EarlyBound.CurrentBadPoints.Add(dv); } } EarlyBound.DerivationType = BoundingValueType.SteppedInterpolation; } } } if (state.HasTerminated && (state.LatePoint == null)) { EarlyBound.CurrentBadPoints = new List <DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) { if (dv.SourceTimestamp < EarlyBound.Timestamp) { EarlyBound.CurrentBadPoints.Add(dv); } } EarlyBound.DerivationType = BoundingValueType.SteppedExtrapolation; } } if (bucket.EndMatch(state.LatestTimestamp) && StatusCode.IsGood(state.LatestStatus)) { LateBound.RawPoint = state.LatePoint == null ? state.EarlyPoint : state.LatePoint; LateBound.DerivationType = BoundingValueType.Raw; } else { if (LateBound.DerivationType != BoundingValueType.Raw) { if ((state.EarlyPoint != null) && (state.EarlyPoint.SourceTimestamp < bucket.To)) { LateBound.EarlyPoint = state.EarlyPoint; } if (LateBound.LatePoint == null) { if ((state.LatePoint != null) && (state.LatePoint.SourceTimestamp >= bucket.To)) { LateBound.CurrentBadPoints = new List <DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) { if (dv.SourceTimestamp < LateBound.Timestamp) { LateBound.CurrentBadPoints.Add(dv); } } LateBound.DerivationType = BoundingValueType.SteppedInterpolation; } } } if (state.HasTerminated && (state.LatePoint == null)) { LateBound.CurrentBadPoints = new List <DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) { if (dv.SourceTimestamp < LateBound.Timestamp) { LateBound.CurrentBadPoints.Add(dv); } } if (EarlyBound.PriorPoint == null) { EarlyBound.PriorPoint = state.PriorPoint; EarlyBound.PriorBadPoints = state.PriorBadPoints; EarlyBound.DerivationType = UseSlopedExtrapolation ? BoundingValueType.SlopedExtrapolation : BoundingValueType.SteppedExtrapolation; } LateBound.DerivationType = BoundingValueType.SteppedExtrapolation; } } }
/// <summary> /// Returns true if more data is required for the next interval. /// </summary> public abstract bool WaitForMoreData(TimeSlice bucket, AggregateState state);
/// <summary> /// Updates the bounding values for the time slice. /// </summary> public abstract void UpdateBoundingValues(TimeSlice bucket, AggregateState state);
/// <summary> /// Returns true if more data is required for the next interval. /// </summary> public override bool WaitForMoreData(TimeSlice bucket, AggregateState state) { bool wait = false; if (!state.HasTerminated) { if (bucket.ContainsTime(state.LatestTimestamp)) { wait = true; } } return wait; }
/// <summary> /// Initializes the aggregation. /// </summary> private void InitializeAggregation() { _state = new AggregateState(this, this); }
/// <summary> /// Returns true if more data is required for the next interval. /// </summary> public override bool WaitForMoreData(TimeSlice bucket, AggregateState state) { if (!state.HasTerminated) { if (bucket.ContainsTime(state.LatestTimestamp)) { return true; } if (this.IsReverseAggregation) { if (state.LatestTimestamp < bucket.To) { return false; } } else { if (state.LatestTimestamp > bucket.To) { return false; } } if ((bucket.EarlyBound.Value == null) || (bucket.LateBound.Value == null)) { return true; } } return false; }
/// <summary> /// Updates the bounding values. /// </summary> public override void UpdateBoundingValues(TimeSlice bucket, AggregateState state) { base.UpdateBoundingValues(bucket, state); UpdatePriorPoint(bucket.EarlyBound, state); }
/// <summary> /// Updates the bounding values for the time slice. /// </summary> public override void UpdateBoundingValues(TimeSlice bucket, AggregateState state) { BoundingValue EarlyBound = bucket.EarlyBound; BoundingValue LateBound = bucket.LateBound; if (bucket.ExactMatch(state.LatestTimestamp) && StatusCode.IsGood(state.LatestStatus)) { EarlyBound.RawPoint = state.LatePoint == null ? state.EarlyPoint : state.LatePoint; EarlyBound.DerivationType = BoundingValueType.Raw; } else { if (EarlyBound.DerivationType != BoundingValueType.Raw) { if (EarlyBound.EarlyPoint == null) { if ((state.EarlyPoint != null) && (state.EarlyPoint.SourceTimestamp < bucket.From)) { EarlyBound.EarlyPoint = state.EarlyPoint; } } if (EarlyBound.LatePoint == null) { if ((state.LatePoint != null) && (state.LatePoint.SourceTimestamp >= bucket.From)) { EarlyBound.LatePoint = state.LatePoint; if (SteppedVariable) { EarlyBound.CurrentBadPoints = new List<DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) if (dv.SourceTimestamp < EarlyBound.Timestamp) EarlyBound.CurrentBadPoints.Add(dv); } else { EarlyBound.CurrentBadPoints = state.CurrentBadPoints; } EarlyBound.DerivationType = SteppedVariable ? BoundingValueType.SteppedInterpolation : BoundingValueType.SlopedInterpolation; } } } if (state.HasTerminated && (state.LatePoint == null)) { if (SteppedVariable) { EarlyBound.CurrentBadPoints = new List<DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) if (dv.SourceTimestamp < EarlyBound.Timestamp) EarlyBound.CurrentBadPoints.Add(dv); } else { EarlyBound.CurrentBadPoints = state.CurrentBadPoints; } } } if (bucket.EndMatch(state.LatestTimestamp) && StatusCode.IsGood(state.LatestStatus)) { LateBound.RawPoint = state.LatePoint == null ? state.EarlyPoint : state.LatePoint; LateBound.DerivationType = BoundingValueType.Raw; } else { if (LateBound.DerivationType != BoundingValueType.Raw) { if ((state.EarlyPoint != null) && (state.EarlyPoint.SourceTimestamp < bucket.To)) LateBound.EarlyPoint = state.EarlyPoint; if (LateBound.LatePoint == null) { if ((state.LatePoint != null) && (state.LatePoint.SourceTimestamp >= bucket.To)) { LateBound.LatePoint = state.LatePoint; if (SteppedVariable) { LateBound.CurrentBadPoints = new List<DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) if (dv.SourceTimestamp < LateBound.Timestamp) LateBound.CurrentBadPoints.Add(dv); } else { LateBound.CurrentBadPoints = state.CurrentBadPoints; } LateBound.DerivationType = SteppedVariable ? BoundingValueType.SteppedInterpolation : BoundingValueType.SlopedInterpolation; } } } if (state.HasTerminated && (state.LatePoint == null)) { if (SteppedVariable) { LateBound.CurrentBadPoints = new List<DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) if (dv.SourceTimestamp < LateBound.Timestamp) LateBound.CurrentBadPoints.Add(dv); } else { LateBound.CurrentBadPoints = state.CurrentBadPoints; } } UpdatePriorPoint(LateBound, state); } }
/// <summary> /// Updates the value for the time slice. /// </summary> public override DataValue Compute(IAggregationContext context, TimeSlice bucket, AggregateState state) { DataValue retval = new DataValue { SourceTimestamp = bucket.From }; StatusCode code = StatusCodes.BadNoData; DataValue boundValue = context.IsReverseAggregation ? bucket.LateBound.Value : bucket.EarlyBound.Value; if (boundValue != null) { code = bucket.EarlyBound.Value.StatusCode.Code; code.AggregateBits = bucket.EarlyBound.Value.StatusCode.AggregateBits; retval.Value = Convert.ToDouble(bucket.EarlyBound.Value.Value, CultureInfo.InvariantCulture); } if (bucket.Incomplete) { code.AggregateBits |= AggregateBits.Partial; } retval.StatusCode = code; return(retval); }
/// <summary> /// Updates the bounding values for the time slice. /// </summary> public override void UpdateBoundingValues(TimeSlice bucket, AggregateState state) { BoundingValue EarlyBound = bucket.EarlyBound; BoundingValue LateBound = bucket.LateBound; if (bucket.ExactMatch(state.LatestTimestamp)) { EarlyBound.RawPoint = state.LatePoint == null ? state.EarlyPoint : state.LatePoint; EarlyBound.DerivationType = BoundingValueType.QualityRaw; } else { if (EarlyBound.DerivationType != BoundingValueType.QualityRaw) { if (EarlyBound.EarlyPoint == null) { if ((state.EarlyPoint != null) && (state.EarlyPoint.SourceTimestamp < bucket.From)) { EarlyBound.EarlyPoint = state.EarlyPoint; } } if (EarlyBound.LatePoint == null) { if ((state.LatePoint != null) && (state.LatePoint.SourceTimestamp >= bucket.From)) { EarlyBound.CurrentBadPoints = new List<DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) if (dv.SourceTimestamp < EarlyBound.Timestamp) EarlyBound.CurrentBadPoints.Add(dv); EarlyBound.DerivationType = BoundingValueType.QualityInterpolation; } } } if (state.HasTerminated && (state.LatePoint == null)) { EarlyBound.CurrentBadPoints = new List<DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) if (dv.SourceTimestamp < EarlyBound.Timestamp) EarlyBound.CurrentBadPoints.Add(dv); EarlyBound.DerivationType = BoundingValueType.QualityExtrapolation; } } if (bucket.EndMatch(state.LatestTimestamp)) { LateBound.RawPoint = state.LatePoint == null ? state.EarlyPoint : state.LatePoint; LateBound.DerivationType = BoundingValueType.QualityRaw; } else { if (LateBound.DerivationType != BoundingValueType.QualityRaw) { if ((state.EarlyPoint != null) && (state.EarlyPoint.SourceTimestamp < bucket.To)) LateBound.EarlyPoint = state.EarlyPoint; if (LateBound.LatePoint == null) { if ((state.LatePoint != null) && (state.LatePoint.SourceTimestamp >= bucket.To)) { LateBound.CurrentBadPoints = new List<DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) if (dv.SourceTimestamp < LateBound.Timestamp) LateBound.CurrentBadPoints.Add(dv); LateBound.DerivationType = BoundingValueType.QualityInterpolation; } } } if (state.HasTerminated && (state.LatePoint == null)) { LateBound.CurrentBadPoints = new List<DataValue>(); foreach (DataValue dv in state.CurrentBadPoints) if (dv.SourceTimestamp < LateBound.Timestamp) LateBound.CurrentBadPoints.Add(dv); LateBound.DerivationType = BoundingValueType.QualityExtrapolation; } } }
/// <summary> /// Updates the data processed by the aggregator. /// </summary> public void UpdateProcessedData(DataValue rawValue, AggregateState state) { // step 1: compute new TimeSlice instances to enqueue, until we reach the one the // rawValue belongs in or we've reached the one that goes to the EndTime. Ensure // that the raw value is added to the last one created. TimeSlice tmpTS = null; if (m_pending == null) m_pending = new Queue<TimeSlice>(); if (m_latest == null) { tmpTS = TimeSlice.CreateInitial(StartTime, EndTime, ProcessingInterval); if (tmpTS != null) { m_pending.Enqueue(tmpTS); m_latest = tmpTS; } } else { tmpTS = m_latest; } DateTime latestTime = (StartTime > EndTime) ? StartTime : EndTime; while ((tmpTS != null) && (state.HasTerminated || !tmpTS.AcceptValue(rawValue))) { tmpTS = TimeSlice.CreateNext(latestTime, ProcessingInterval, tmpTS); if (tmpTS != null) { m_pending.Enqueue(tmpTS); m_latest = tmpTS; } } // step 2: apply the aggregator to the head of the queue to see if we can convert // it into a processed point. If so, dequeue it and add the processed value to the // m_released list. Keep doing it until one of the TimeSlices returns null or we // run out of enqueued TimeSlices (should only happen on termination). if (m_released == null) m_released = new List<DataValue>(); foreach (TimeSlice b in m_pending) UpdateBoundingValues(b, state); bool active = true; while ((m_pending.Count > 0) && active) { TimeSlice top = m_pending.Peek(); DataValue computed = null; if (!WaitForMoreData(top, state)) computed = Compute(this, top, state); if (computed != null) { m_released.Add(computed); m_pending.Dequeue(); } else { active = false; } } }
/// <summary> /// Calculates the value for the time slice. /// </summary> public override DataValue Compute(IAggregationContext context, TimeSlice bucket, AggregateState state) { var retval = new DataValue { SourceTimestamp = bucket.From }; StatusCode code = StatusCodes.Good; var previous = new DataValue { SourceTimestamp = bucket.From }; if (bucket.EarlyBound.Value != null) { previous.StatusCode = (StatusCode)bucket.EarlyBound.Value.WrappedValue.Value; } else { previous.StatusCode = StatusCodes.Bad; } if (!RightStatusCode(previous)) { previous = null; } var total = 0.0; foreach (var v in bucket.Values) { if (previous != null) { total += (v.SourceTimestamp - previous.SourceTimestamp).TotalMilliseconds; } if (RightStatusCode(v)) { previous = v; } else { previous = null; } } if (previous != null) { total += (bucket.To - previous.SourceTimestamp).TotalMilliseconds; } retval.Value = total; code.AggregateBits = AggregateBits.Calculated; if (bucket.Incomplete) { code.AggregateBits |= AggregateBits.Partial; } retval.StatusCode = code; return(retval); }