rusEFI
The most advanced open source ECU
Loading...
Searching...
No Matches
interpolation.cpp
Go to the documentation of this file.
1/**
2 * @file interpolation.cpp
3 * @brief Linear interpolation algorithms
4 *
5 * See test_interpolation_3d.cpp
6 *
7 *
8 * @date Oct 17, 2013
9 * @author Andrey Belomutskiy, (c) 2012-2020
10 * @author Dmitry Sidin, (c) 2015
11 */
12
13#include "pch.h"
14
15#include "efi_interpolation.h"
16
17/** @brief Linear interpolation by two points
18 *
19 * @param x1 key of the first point
20 * @param y1 value of the first point
21 * @param x2 key of the second point
22 * @param y2 value of the second point
23 * @param X key to be interpolated
24 *
25 * @note For example, "interpolateMsg("", engineConfiguration.tpsMin, 0, engineConfiguration.tpsMax, 100, adc);"
26 * @see interpolateClamped
27 */
28float interpolateMsg(const char *msg, float x1, float y1, float x2, float y2, float x) {
29 if (std::isnan(x1) || std::isnan(x2) || std::isnan(y1) || std::isnan(y2)) {
30 warning(ObdCode::CUSTOM_ERR_INTERPOLATE_1, "interpolate%s: why param", msg);
31 return NAN;
32 }
33 if (std::isnan(x)) {
34 warning(ObdCode::CUSTOM_ERR_INTERPOLATE_2, "interpolate%s: why X", msg);
35 return NAN;
36 }
37 // todo: double comparison using EPS
38 if (x1 == x2) {
39 /**
40 * we could end up here for example while resetting bins while changing engine type
41 */
42 warning(ObdCode::CUSTOM_ERR_INTERPOLATE_3, "interpolate%s: Same x1 and x2 in interpolate: %.2f/%.2f", msg, x1, x2);
43 return NAN;
44 }
45
46 // a*x1 + b = y1
47 // a*x2 + b = y2
48// efiAssertVoid(ObdCode::CUSTOM_ERR_ASSERT_VOID, x1 != x2, "no way we can interpolate");
49 float a = INTERPOLATION_A(x1, y1, x2, y2);
50 if (std::isnan(a)) {
51 warning(ObdCode::CUSTOM_ERR_INTERPOLATE_4, "interpolate%s: why a", msg);
52 return NAN;
53 }
54 float b = y1 - a * x1;
55 return a * x + b;
56}
57
58float interpolateClampedWithValidation(float x1, float y1, float x2, float y2, float x) {
59 if (x1 >= x2) {
60 criticalError("interpolateClamped %f has to be smaller than %f", x1, x2);
61 }
62 return interpolateClamped(x1, y1, x2, y2, x);
63}
64
65/**
66 * todo: use 'interpolateClampedWithValidation' wider?
67 * @see interpolateMsg
68 */
69float interpolateClamped(float x1, float y1, float x2, float y2, float x) {
70 // note how we assume order of x1 and x2 here! see also interpolateClampedWithValidation
71 if (x <= x1)
72 return y1;
73 if (x >= x2)
74 return y2;
75
76 // todo: do we care with code duplication with interpolateMsg above?
77 float a = INTERPOLATION_A(x1, y1, x2, y2);
78 float b = y1 - a * x1;
79 return a * x + b;
80}
bool warning(ObdCode code, const char *fmt,...)
float interpolateMsg(const char *msg, float x1, float y1, float x2, float y2, float x)
Linear interpolation by two points.
float interpolateClampedWithValidation(float x1, float y1, float x2, float y2, float x)
float interpolateClamped(float x1, float y1, float x2, float y2, float x)
@ CUSTOM_ERR_INTERPOLATE_3
@ CUSTOM_ERR_INTERPOLATE_4
@ CUSTOM_ERR_INTERPOLATE_2
@ CUSTOM_ERR_INTERPOLATE_1