From aa8b569eb652c22821b93a6e543449a52ad21158 Mon Sep 17 00:00:00 2001 From: Lajos Molnar Date: Tue, 22 Apr 2014 16:31:54 -0700 Subject: stagefright: add ClockEstimator API and WindowedLinearFitEstimator Change-Id: I74474c385848a8eab2ac0da7c069510378e2b217 --- include/media/stagefright/ClockEstimator.h | 110 +++++++++++++++++++++++++++++ 1 file changed, 110 insertions(+) create mode 100644 include/media/stagefright/ClockEstimator.h (limited to 'include') diff --git a/include/media/stagefright/ClockEstimator.h b/include/media/stagefright/ClockEstimator.h new file mode 100644 index 0000000..2fd6e75 --- /dev/null +++ b/include/media/stagefright/ClockEstimator.h @@ -0,0 +1,110 @@ +/* +** +** Copyright 2014, The Android Open Source Project +** +** Licensed under the Apache License, Version 2.0 (the "License"); +** you may not use this file except in compliance with the License. +** You may obtain a copy of the License at +** +** http://www.apache.org/licenses/LICENSE-2.0 +** +** Unless required by applicable law or agreed to in writing, software +** distributed under the License is distributed on an "AS IS" BASIS, +** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +** See the License for the specific language governing permissions and +** limitations under the License. +*/ + +#ifndef CLOCK_ESTIMATOR_H_ + +#define CLOCK_ESTIMATOR_H_ + + +#include +#include + +namespace android { +// --------------------------------------------------------------------------- + +struct ClockEstimator : RefBase { + virtual double estimate(double x, double y) = 0; + virtual void reset() = 0; +}; + +struct WindowedLinearFitEstimator : ClockEstimator { + struct LinearFit { + /** + * Fit y = a * x + b, where each input has a weight + */ + double mX; // sum(w_i * x_i) + double mXX; // sum(w_i * x_i^2) + double mY; // sum(w_i * y_i) + double mYY; // sum(w_i * y_i^2) + double mXY; // sum(w_i * x_i * y_i) + double mW; // sum(w_i) + + LinearFit(); + void reset(); + void combine(const LinearFit &lf); + void add(double x, double y, double w); + void scale(double w); + double interpolate(double x); + double size() const; + + DISALLOW_EVIL_CONSTRUCTORS(LinearFit); + }; + + /** + * Estimator for f(x) = y' where input y' is noisy, but + * theoretically linear: + * + * y' =~ y = a * x + b + * + * It uses linear fit regression over a tapering rolling window + * to get an estimate for y (from the current and past inputs + * (x, y')). + * + * ____________ + * /| |\ + * / | | \ + * / | | \ <--- new data (x, y') + * / | main | \ + * <--><----------><--> + * tail head + * + * weight is 1 under the main window, tapers exponentially by + * the factors given in the head and the tail. + * + * Assuming that x and y' are monotonic, that x is somewhat + * evenly sampled, and that a =~ 1, the estimated y is also + * going to be monotonic. + */ + WindowedLinearFitEstimator( + size_t headLength = 5, double headFactor = 0.5, + size_t mainLength = 0, double tailFactor = 0.99); + + virtual void reset(); + + // add a new sample (x -> y') and return an estimated value for the true y + virtual double estimate(double x, double y); + +private: + Vector mXHistory; // circular buffer + Vector mYHistory; // circular buffer + LinearFit mHead; + LinearFit mMain; + LinearFit mTail; + double mHeadFactorInv; + double mTailFactor; + double mFirstWeight; + size_t mHistoryLength; + size_t mHeadLength; + size_t mNumSamples; + size_t mSampleIx; + + DISALLOW_EVIL_CONSTRUCTORS(WindowedLinearFitEstimator); +}; + +}; // namespace android + +#endif -- cgit v1.1