ESPHome 2026.11.0-dev
Loading...
Searching...
No Matches
filter.h
Go to the documentation of this file.
1#pragma once
2
4#ifdef USE_SENSOR_FILTER
5
6#include <array>
7#include <utility>
8#include <vector>
12
13namespace esphome::sensor {
14
15class Sensor;
16
22class Filter {
23 public:
33 virtual optional<float> new_value(float value) = 0;
34
36 virtual void initialize(Sensor *parent, Filter *next);
37
38 void input(float value);
39
40 void output(float value);
41
42 protected:
43 friend Sensor;
44
45 Filter *next_{nullptr};
46 Sensor *parent_{nullptr};
47};
48
55 public:
56 SlidingWindowFilter(uint16_t window_size, uint16_t send_every, uint16_t send_first_at);
57
58 optional<float> new_value(float value) final;
59
60 protected:
62 virtual float compute_result() = 0;
63
66 uint16_t send_every_;
67 uint16_t send_at_;
68};
69
75 public:
77
78 protected:
81 template<typename Compare> float find_extremum_() {
82 float result = NAN;
83 Compare comp;
84 for (float v : this->window_) {
85 if (!std::isnan(v)) {
86 result = std::isnan(result) ? v : (comp(v, result) ? v : result);
87 }
88 }
89 return result;
90 }
91};
92
107
113 public:
123 explicit QuantileFilter(size_t window_size, size_t send_every, size_t send_first_at, float quantile);
124
125 void set_quantile(float quantile) { this->quantile_ = quantile; }
126
127 protected:
128 float compute_result() override;
130};
131
137 public:
146 using SortedWindowFilter::SortedWindowFilter;
147
148 protected:
149 float compute_result() override;
150};
151
156class SkipInitialFilter : public Filter {
157 public:
162 explicit SkipInitialFilter(size_t num_to_ignore);
163
164 optional<float> new_value(float value) override;
165
166 protected:
168};
169
174class MinFilter : public MinMaxFilter {
175 public:
184 using MinMaxFilter::MinMaxFilter;
185
186 protected:
187 float compute_result() override;
188};
189
194class MaxFilter : public MinMaxFilter {
195 public:
204 using MinMaxFilter::MinMaxFilter;
205
206 protected:
207 float compute_result() override;
208};
209
216 public:
226
227 protected:
228 float compute_result() override;
229};
230
237 public:
238 ExponentialMovingAverageFilter(float alpha, uint16_t send_every, uint16_t send_first_at);
239
240 optional<float> new_value(float value) override;
241
242 void set_send_every(uint16_t send_every) { this->send_every_ = send_every; }
243 void set_alpha(float alpha) { this->alpha_ = alpha; }
244
245 protected:
246 float accumulator_{NAN};
247 float alpha_;
248 uint16_t send_every_;
249 uint16_t send_at_;
250 bool first_value_{true};
251};
252
258 public:
259 explicit ThrottleAverageFilter(uint32_t time_period);
260
261 void initialize(Sensor *parent, Filter *next) override;
262
263 optional<float> new_value(float value) override;
264
265 protected:
266 float sum_{0.0f};
268 // Sample count packed with NaN-seen flag in a single 32-bit word.
269 // n_ is bounded by YAML cap on time_period_ (24 h) × max plausible source
270 // rate (1 kHz) = 86.4M ≪ 2^31, so 31 bits has 25x headroom.
271 uint32_t n_ : 31 {0};
273};
274
275using lambda_filter_t = std::function<optional<float>(float)>;
276
284class LambdaFilter : public Filter {
285 public:
286 explicit LambdaFilter(lambda_filter_t lambda_filter);
287
288 optional<float> new_value(float value) override;
289
290 const lambda_filter_t &get_lambda_filter() const;
291 void set_lambda_filter(const lambda_filter_t &lambda_filter);
292
293 protected:
295};
296
303 public:
304 explicit StatelessLambdaFilter(optional<float> (*lambda_filter)(float)) : lambda_filter_(lambda_filter) {}
305
306 optional<float> new_value(float value) override { return this->lambda_filter_(value); }
307
308 protected:
309 optional<float> (*lambda_filter_)(float);
310};
311
313class OffsetFilter : public Filter {
314 public:
315 explicit OffsetFilter(TemplatableFn<float> offset);
316
317 optional<float> new_value(float value) override;
318
319 protected:
321};
322
324class MultiplyFilter : public Filter {
325 public:
326 explicit MultiplyFilter(TemplatableFn<float> multiplier);
327 optional<float> new_value(float value) override;
328
329 protected:
331};
332
333// Value tables are read in place from flash, which ESP8266 only allows for whole words.
334static_assert(sizeof(TemplatableFn<float>) == sizeof(void *), "TemplatableFn<float> must stay a single pointer");
335
337class ValueListFilter : public Filter {
338 protected:
339 explicit ValueListFilter(const TemplatableFn<float> *values) : values_(values) {}
340
342 bool value_matches_any_(float sensor_value);
343
344 // Shared PROGMEM table ended by an empty entry, so no count is stored; entries are function
345 // pointers, so aligned 32-bit loads from flash are safe on ESP8266.
347};
348
351 public:
352 explicit FilterOutValueFilter(const TemplatableFn<float> *values_to_filter_out)
353 : ValueListFilter(values_to_filter_out) {}
354
355 optional<float> new_value(float value) override {
356 if (this->value_matches_any_(value))
357 return {}; // Filter out
358 return value; // Pass through
359 }
360};
361
362class ThrottleFilter : public Filter {
363 public:
364 explicit ThrottleFilter(uint32_t min_time_between_inputs);
365
366 optional<float> new_value(float value) override;
367
368 protected:
371};
372
375 public:
376 ThrottleWithPriorityFilter(uint32_t min_time_between_inputs, const TemplatableFn<float> *prioritized_values)
377 : ValueListFilter(prioritized_values), min_time_between_inputs_(min_time_between_inputs) {}
378
379 optional<float> new_value(float value) override;
380
381 protected:
384};
385
389 public:
390 explicit ThrottleWithPriorityNanFilter(uint32_t min_time_between_inputs);
391
392 optional<float> new_value(float value) override;
393
394 protected:
397};
398
399// Base class for timeout filters - contains common loop logic.
400//
401// Why this intentionally inherits Component (and does NOT use the self-keyed
402// `App.scheduler.set_timeout(this, ...)` pattern that the other Filter classes
403// migrated to):
404//
405// Timeout filters re-arm on every input, so on devices with many sensors
406// using timeout filters (e.g. multi-LD2450 boards) every armed filter would
407// require a live SchedulerItem in RAM at the same time. A SchedulerItem is
408// substantially larger than the Component bookkeeping bytes carried by this
409// class, so paying the Component cost per filter (one-time, BSS) is cheaper
410// than paying for a SchedulerItem per filter (live, while armed). #11922
411// is the original symptom and switchover to the loop-based design; #16173
412// attempted to migrate this onto the scheduler and was closed for exactly
413// this reason — even if the scheduler pool were unbounded, RAM per armed
414// filter would still be dominated by the SchedulerItem itself, not by
415// anything we can shrink in the scheduler.
416//
417// The loop-based design has additional advantages on top of the RAM win:
418// `enable_loop()` / `disable_loop()` partitions the cost away when no
419// timeout is armed; while armed, work is a single timestamp compare per
420// active filter, with no per-input scheduler cancel/insert path.
421//
422// Don't try to migrate this class onto the self-keyed scheduler. The math
423// doesn't work — at scale, this design is the smaller one.
424class TimeoutFilterBase : public Filter, public Component {
425 public:
426 void loop() override;
427 float get_setup_priority() const override;
428
429 protected:
430 explicit TimeoutFilterBase(uint32_t time_period) : time_period_(time_period) { this->disable_loop(); }
431 virtual float get_output_value() = 0;
432
433 uint32_t time_period_; // 4 bytes (timeout duration in ms)
434 uint32_t timeout_start_time_{0}; // 4 bytes (when the timeout was started)
435 // Total base: 8 bytes
436};
437
438// Timeout filter for "last" mode - outputs the last received value after timeout
440 public:
441 explicit TimeoutFilterLast(uint32_t time_period) : TimeoutFilterBase(time_period) {}
442
443 optional<float> new_value(float value) override;
444
445 protected:
446 float get_output_value() override { return this->pending_value_; }
447 float pending_value_{0}; // 4 bytes (value to output when timeout fires)
448 // Total: 8 (base) + 4 = 12 bytes + vtable ptr + Component overhead
449};
450
451// Timeout filter with configured value - evaluates TemplatableValue after timeout
453 public:
456
457 optional<float> new_value(float value) override;
458
459 protected:
460 float get_output_value() override { return this->value_.value(); }
461 TemplatableFn<float> value_; // 4 bytes (configured output value, can be lambda)
462 // Total: 8 (base) + 4 = 12 bytes + vtable ptr + Component overhead
463};
464
468 public:
469 explicit TimeoutThrottleFilter(uint32_t time_period) : TimeoutFilterLast(time_period) {}
470
471 optional<float> new_value(float value) override;
472 void loop() override;
473
474 protected:
475 uint32_t last_input_{0}; // When the throttle stage last let a value through
476};
477
478class DebounceFilter : public Filter {
479 public:
480 explicit DebounceFilter(uint32_t time_period);
481
482 optional<float> new_value(float value) override;
483
484 protected:
486};
487
488class HeartbeatFilter : public Filter {
489 public:
490 explicit HeartbeatFilter(uint32_t time_period);
491
492 void initialize(Sensor *parent, Filter *next) override;
493 optional<float> new_value(float value) override;
494
495 void set_optimistic(bool optimistic) { this->optimistic_ = optimistic; }
496
497 protected:
500 bool has_value_{false};
501 bool optimistic_{false};
502};
503
504class DeltaFilter : public Filter {
505 public:
506 explicit DeltaFilter(float min_a0, float min_a1, float max_a0, float max_a1);
507
508 void set_baseline(float (*fn)(float));
509
510 optional<float> new_value(float value) override;
511
512 protected:
513 // These values represent linear equations for the min and max values but in practice only one of a0 and a1 will be
514 // non-zero Each limit is calculated as fabs(a0 + value * a1)
515
517 // default baseline is the previous value
518 float (*baseline_)(float) = [](float last_value) { return last_value; };
519
520 float last_value_{NAN};
521};
522
524void or_filter_initialize(Filter **filters, size_t count, Sensor *parent, Filter *phi);
525optional<float> or_filter_new_value(Filter **filters, size_t count, float value, bool &has_value);
526
528template<size_t N> class OrFilter : public Filter {
529 public:
530 explicit OrFilter(std::initializer_list<Filter *> filters) { init_array_from(this->filters_, filters); }
531 // Codegen passes each filter as its own argument; a list literal would sit in .rodata (RAM on ESP8266).
532 template<typename... Fs>
533 requires(sizeof...(Fs) == N)
534 explicit OrFilter(Fs *...filters) : filters_{filters...} {}
535
536 void initialize(Sensor *parent, Filter *next) override {
537 Filter::initialize(parent, next);
538 or_filter_initialize(this->filters_.data(), N, parent, &this->phi_);
539 }
540
541 optional<float> new_value(float value) override {
542 return or_filter_new_value(this->filters_.data(), N, value, this->has_value_);
543 }
544
545 protected:
546 class PhiNode : public Filter {
547 public:
548 PhiNode(OrFilter *or_parent) : or_parent_(or_parent) {}
549 optional<float> new_value(float value) override {
550 if (!this->or_parent_->has_value_) {
551 this->or_parent_->output(value);
552 this->or_parent_->has_value_ = true;
553 }
554 return {};
555 }
556
557 protected:
559 };
560
561 std::array<Filter *, N> filters_{};
563 bool has_value_{false};
564};
565
568 public:
569 explicit CalibrateLinearFilter(const std::array<float, 3> *functions) : functions_(functions) {}
570 optional<float> new_value(float value) override;
571
572 protected:
573 const std::array<float, 3> *functions_; // Last segment has a NaN boundary, which ends the table
574};
575
578 public:
579 explicit CalibratePolynomialFilter(const float *coefficients) : coefficients_(coefficients) {}
580 optional<float> new_value(float value) override;
581
582 protected:
583 const float *coefficients_; // [count, c0, c1, ...]
584};
585
586class ClampFilter : public Filter {
587 public:
588 ClampFilter(float min, float max, bool ignore_out_of_range);
589 optional<float> new_value(float value) override;
590
591 protected:
592 float min_{NAN};
593 float max_{NAN};
595};
596
597class RoundFilter : public Filter {
598 public:
599 explicit RoundFilter(uint8_t precision);
600 optional<float> new_value(float value) override;
601
602 protected:
603 uint8_t precision_;
604};
605
607 public:
608 explicit RoundMultipleFilter(float multiple);
609 optional<float> new_value(float value) override;
610
611 protected:
613};
614
615template<uint8_t Digits> class RoundSignificantDigitsFilter : public Filter {
616 public:
617 optional<float> new_value(float value) override {
618 if (std::isfinite(value)) {
619 if (value == 0.0f)
620 return 0.0f;
621 float factor = pow10_int(Digits - 1 - ilog10(value));
622 return roundf(value * factor) / factor;
623 }
624 return value;
625 }
626};
627
629 public:
630 ToNTCResistanceFilter(double a, double b, double c) : a_(a), b_(b), c_(c) {}
631 optional<float> new_value(float value) override;
632
633 protected:
634 double a_;
635 double b_;
636 double c_;
637};
638
640 public:
641 ToNTCTemperatureFilter(double a, double b, double c) : a_(a), b_(b), c_(c) {}
642 optional<float> new_value(float value) override;
643
644 protected:
645 double a_;
646 double b_;
647 double c_;
648};
649
657 public:
658 RHCorrectionFilter(TemplatableFn<float> offset, const Sensor *temperature_sensor, bool use_fahrenheit)
659 : temperature_offset_(offset), temperature_sensor_(temperature_sensor), use_fahrenheit_(use_fahrenheit) {}
660
661 optional<float> new_value(float value) override;
662
663 protected:
667 bool warned_{false};
668};
669
675class StreamingFilter : public Filter {
676 public:
677 StreamingFilter(uint16_t window_size, uint16_t send_first_at);
678
679 optional<float> new_value(float value) final;
680
681 protected:
683 virtual void process_value(float value) = 0;
684
686 virtual float compute_batch_result() = 0;
687
689 virtual void reset_batch() = 0;
690
691 uint16_t window_size_;
692 uint16_t count_{0};
694 bool first_send_{true};
695};
696
702 public:
704
705 protected:
706 void process_value(float value) override;
707 float compute_batch_result() override;
708 void reset_batch() override;
709
710 float current_min_{NAN};
711};
712
718 public:
720
721 protected:
722 void process_value(float value) override;
723 float compute_batch_result() override;
724 void reset_batch() override;
725
726 float current_max_{NAN};
727};
728
734 public:
736
737 protected:
738 void process_value(float value) override;
739 float compute_batch_result() override;
740 void reset_batch() override;
741
742 float sum_{0.0f};
743 size_t valid_count_{0};
744};
745
746} // namespace esphome::sensor
747
748#endif // USE_SENSOR_FILTER
void disable_loop()
Disable this component's loop.
Fixed-capacity circular buffer - allocates once at runtime, never reallocates.
Definition helpers.h:469
Fixed-capacity vector - sized once through init() or try_init(); push_back never reallocates This avo...
Definition helpers.h:624
Function-pointer-only templatable storage (4 bytes on 32-bit).
Definition automation.h:20
T value(X... x) const
Definition automation.h:68
Piecewise linear calibration; the segments are a PROGMEM table shared by filters with the same data.
Definition filter.h:567
optional< float > new_value(float value) override
Definition filter.cpp:418
const std::array< float, 3 > * functions_
Definition filter.h:573
CalibrateLinearFilter(const std::array< float, 3 > *functions)
Definition filter.h:569
Polynomial calibration; the coefficients are a PROGMEM table shared by filters with the same data.
Definition filter.h:577
CalibratePolynomialFilter(const float *coefficients)
Definition filter.h:579
optional< float > new_value(float value) override
Definition filter.cpp:426
ClampFilter(float min, float max, bool ignore_out_of_range)
Definition filter.cpp:437
optional< float > new_value(float value) override
Definition filter.cpp:439
optional< float > new_value(float value) override
Definition filter.cpp:383
DebounceFilter(uint32_t time_period)
Definition filter.cpp:389
void set_baseline(float(*fn)(float))
Definition filter.cpp:288
DeltaFilter(float min_a0, float min_a1, float max_a0, float max_a1)
Definition filter.cpp:285
optional< float > new_value(float value) override
Definition filter.cpp:290
float(* baseline_)(float)
Definition filter.h:518
Simple exponential moving average filter.
Definition filter.h:236
void set_send_every(uint16_t send_every)
Definition filter.h:242
optional< float > new_value(float value) override
Definition filter.cpp:158
ExponentialMovingAverageFilter(float alpha, uint16_t send_every, uint16_t send_first_at)
Definition filter.cpp:156
Apply a filter to sensor values such as moving average.
Definition filter.h:22
virtual optional< float > new_value(float value)=0
This will be called every time the filter receives a new value.
void output(float value)
Definition filter.cpp:34
virtual void initialize(Sensor *parent, Filter *next)
Initialize this filter, please note this can be called more than once.
Definition filter.cpp:43
void input(float value)
Definition filter.cpp:28
A simple filter that only forwards the filter chain if it doesn't receive value_to_filter_out.
Definition filter.h:350
FilterOutValueFilter(const TemplatableFn< float > *values_to_filter_out)
Definition filter.h:352
optional< float > new_value(float value) override
Definition filter.h:355
HeartbeatFilter(uint32_t time_period)
Definition filter.cpp:392
optional< float > new_value(float value) override
Definition filter.cpp:394
void initialize(Sensor *parent, Filter *next) override
Definition filter.cpp:405
void set_optimistic(bool optimistic)
Definition filter.h:495
This class allows for creation of simple template filters.
Definition filter.h:284
const lambda_filter_t & get_lambda_filter() const
Definition filter.cpp:210
LambdaFilter(lambda_filter_t lambda_filter)
Definition filter.cpp:209
lambda_filter_t lambda_filter_
Definition filter.h:294
void set_lambda_filter(const lambda_filter_t &lambda_filter)
Definition filter.cpp:211
optional< float > new_value(float value) override
Definition filter.cpp:213
Simple max filter.
Definition filter.h:194
float compute_result() override
Definition filter.cpp:140
Simple median filter.
Definition filter.h:136
float compute_result() override
Definition filter.cpp:84
Simple min filter.
Definition filter.h:174
float compute_result() override
Definition filter.cpp:137
Base class for Min/Max filters.
Definition filter.h:74
float find_extremum_()
Helper to find min or max value in window, skipping NaN values Usage: find_extremum_<std::less<float>...
Definition filter.h:81
A simple filter that multiplies to each value it receives by multiplier.
Definition filter.h:324
TemplatableFn< float > multiplier_
Definition filter.h:330
optional< float > new_value(float value) override
Definition filter.cpp:227
MultiplyFilter(TemplatableFn< float > multiplier)
Definition filter.cpp:225
A simple filter that adds offset to each value it receives.
Definition filter.h:313
optional< float > new_value(float value) override
Definition filter.cpp:222
TemplatableFn< float > offset_
Definition filter.h:320
OffsetFilter(TemplatableFn< float > offset)
Definition filter.cpp:220
optional< float > new_value(float value) override
Definition filter.h:549
PhiNode(OrFilter *or_parent)
Definition filter.h:548
N is set by code generation to match the exact number of filters configured in YAML.
Definition filter.h:528
std::array< Filter *, N > filters_
Definition filter.h:561
void initialize(Sensor *parent, Filter *next) override
Definition filter.h:536
optional< float > new_value(float value) override
Definition filter.h:541
OrFilter(Fs *...filters)
Definition filter.h:534
OrFilter(std::initializer_list< Filter * > filters)
Definition filter.h:530
Simple quantile filter.
Definition filter.h:112
float compute_result() override
Definition filter.cpp:123
void set_quantile(float quantile)
Definition filter.h:125
QuantileFilter(size_t window_size, size_t send_every, size_t send_first_at, float quantile)
Construct a QuantileFilter.
Definition filter.cpp:120
RH Temperature correction filter.
Definition filter.h:656
TemplatableFn< float > temperature_offset_
Definition filter.h:664
optional< float > new_value(float value) override
Definition filter.cpp:501
RHCorrectionFilter(TemplatableFn< float > offset, const Sensor *temperature_sensor, bool use_fahrenheit)
Definition filter.h:658
RoundFilter(uint8_t precision)
Definition filter.cpp:456
optional< float > new_value(float value) override
Definition filter.cpp:457
optional< float > new_value(float value) override
Definition filter.cpp:466
optional< float > new_value(float value) override
Definition filter.h:617
Base-class for all sensors.
Definition sensor.h:47
SkipInitialFilter(size_t num_to_ignore)
Construct a SkipInitialFilter.
Definition filter.cpp:107
optional< float > new_value(float value) override
Definition filter.cpp:108
Base class for filters that use a sliding window of values.
Definition filter.h:54
FixedRingBuffer< float > window_
Sliding window ring buffer - automatically overwrites oldest values when full.
Definition filter.h:65
optional< float > new_value(float value) final
Definition filter.cpp:55
SlidingWindowFilter(uint16_t window_size, uint16_t send_every, uint16_t send_first_at)
Definition filter.cpp:50
uint16_t send_every_
Send result every N values.
Definition filter.h:66
virtual float compute_result()=0
Called by new_value() to compute the filtered result from the current window.
uint16_t send_at_
Counter for send_every.
Definition filter.h:67
Simple sliding window moving average filter.
Definition filter.h:215
Base class for filters that need a sorted window (Median, Quantile).
Definition filter.h:98
FixedVector< float > get_window_values_()
Helper to get non-NaN values from the window (not sorted - caller will use nth_element) Returns empty...
Definition filter.cpp:70
Optimized lambda filter for stateless lambdas (no capture).
Definition filter.h:302
optional< float >(* lambda_filter_)(float)
Definition filter.h:309
optional< float > new_value(float value) override
Definition filter.h:306
StatelessLambdaFilter(optional< float >(*lambda_filter)(float))
Definition filter.h:304
Base class for streaming filters (batch windows where window_size == send_every).
Definition filter.h:675
StreamingFilter(uint16_t window_size, uint16_t send_first_at)
Definition filter.cpp:539
virtual void process_value(float value)=0
Called by new_value() to process each value in the batch.
virtual float compute_batch_result()=0
Called by new_value() to compute the result after collecting window_size values.
virtual void reset_batch()=0
Called by new_value() to reset internal state after sending a result.
optional< float > new_value(float value) final
Definition filter.cpp:542
Streaming max filter for batch windows (window_size == send_every).
Definition filter.h:717
void process_value(float value) override
Definition filter.cpp:582
float compute_batch_result() override
Definition filter.cpp:589
Streaming min filter for batch windows (window_size == send_every).
Definition filter.h:701
float compute_batch_result() override
Definition filter.cpp:577
void process_value(float value) override
Definition filter.cpp:570
Streaming moving average filter for batch windows (window_size == send_every).
Definition filter.h:733
void process_value(float value) override
Definition filter.cpp:594
Simple throttle average filter.
Definition filter.h:257
optional< float > new_value(float value) override
Definition filter.cpp:182
ThrottleAverageFilter(uint32_t time_period)
Definition filter.cpp:180
void initialize(Sensor *parent, Filter *next) override
Definition filter.cpp:192
ThrottleFilter(uint32_t min_time_between_inputs)
Definition filter.cpp:254
optional< float > new_value(float value) override
Definition filter.cpp:255
Same as 'throttle' but will immediately publish values contained in value_to_prioritize.
Definition filter.h:374
optional< float > new_value(float value) override
Definition filter.cpp:265
ThrottleWithPriorityFilter(uint32_t min_time_between_inputs, const TemplatableFn< float > *prioritized_values)
Definition filter.h:376
Specialization of ThrottleWithPriorityFilter for the common "prioritize NaN" case: skips the Templata...
Definition filter.h:388
optional< float > new_value(float value) override
Definition filter.cpp:278
ThrottleWithPriorityNanFilter(uint32_t min_time_between_inputs)
Definition filter.cpp:276
TimeoutFilterBase(uint32_t time_period)
Definition filter.h:430
float get_setup_priority() const override
Definition filter.cpp:341
TimeoutFilterConfigured(uint32_t time_period, const TemplatableFn< float > &new_value)
Definition filter.h:454
TemplatableFn< float > value_
Definition filter.h:461
optional< float > new_value(float value) override
Definition filter.cpp:356
float get_output_value() override
Definition filter.h:446
TimeoutFilterLast(uint32_t time_period)
Definition filter.h:441
optional< float > new_value(float value) override
Definition filter.cpp:344
Codegen use only: timeout (value last) followed by throttle_with_priority (NaN only) with the same pe...
Definition filter.h:467
optional< float > new_value(float value) override
Definition filter.cpp:366
TimeoutThrottleFilter(uint32_t time_period)
Definition filter.h:469
optional< float > new_value(float value) override
Definition filter.cpp:473
ToNTCResistanceFilter(double a, double b, double c)
Definition filter.h:630
optional< float > new_value(float value) override
Definition filter.cpp:486
ToNTCTemperatureFilter(double a, double b, double c)
Definition filter.h:641
Base class for filters that compare sensor values against a fixed list of configured values.
Definition filter.h:337
bool value_matches_any_(float sensor_value)
Check if sensor value matches any configured value (with accuracy rounding)
Definition filter.cpp:230
const TemplatableFn< float > * values_
Definition filter.h:346
ValueListFilter(const TemplatableFn< float > *values)
Definition filter.h:339
NameCopy * next
unsigned count
Definition gif.cpp:51
void or_filter_initialize(Filter **filters, size_t count, Sensor *parent, Filter *phi)
Non-template helpers for OrFilter (implementation in filter.cpp)
Definition filter.cpp:313
std::function< optional< float >(float)> lambda_filter_t
Definition filter.h:275
optional< float > or_filter_new_value(Filter **filters, size_t count, float value, bool &has_value)
Definition filter.cpp:320
int8_t ilog10(float value)
Compute floor(log10(fabs(value))) using iterative comparison.
Definition helpers.cpp:569
void init_array_from(std::array< T, N > &dest, std::initializer_list< T > src)
Initialize a std::array from an initializer_list.
Definition helpers.h:599
float pow10_int(int8_t exp)
Compute 10^exp using iterative multiplication/division.
Definition helpers.h:874
static void uint32_t