简体   繁体   English

Arduino的精度更高(浮动)

[英]Better precision with Arduino (floats)

I'm trying to do the Steinhart-Hart temperature calculation on an Arduino. 我正在尝试在Arduino上进行Steinhart-Hart温度计算。 The equation is 等式是 在此处输入图片说明

I solved a system of 3 equations to obtain the values of A, B and C, which are: 我解决了一个由3个方程组成的系统,以获得A,B和C的值,它们分别是:

A = 0.0164872
B = -0.00158538
C = 3.3813e-6

When I plug these into WolframAlpha to solve for T I get a value in Kelvins that makes sense: 当我将它们插入WolframAlpha求解T我会在Kelvins中得到一个有意义的值:

T=1/(0.0164872-0.00158538*log2(10000)+3.3813E-6*(log2(10000))^3) solve for T

T = 298.145 Kelvins = 77 Fahrenheit

However when I try to use this equation on my Arduino, I get a very wrong answer, I suspect because doubles do not have enough precision. 但是,当我尝试在Arduino上使用此方程式时,我得到一个非常错误的答案,我怀疑是因为双精度不够。 Here's what I'm using: 这是我正在使用的:

double temp = (1 / (A + B*log(R_therm) + C*pow(log(R_therm),3)));

This returns 222 Kelvin instead, which is way off. 而是返回222 Kelvin,相距很远。

So, how can I do a calculation like this in Arduino?? 那么,如何在Arduino中进行这样的计算? Any advice is greatly appreciated, thanks. 任何建议,不胜感激,谢谢。

Precision is not the main issue. 精度不是主要问题。 Could even use float and powf() . 甚至可以使用floatpowf() A thermistor temperature calculation is not that accurate. 热敏电阻温度计算不那么精确。 After all the temperature is certainly not better than ±0.1°C accurate . 毕竟温度肯定不比精确的±0.1°C好 Self heating of the thermistor is a larger factor. 热敏电阻的自发热是一个较大的因素。

OP's C code assumes log base 2, use log base e log() as the constants were derived using log base 2. @Martin R OP的C代码假定对数底2,使用日志以e为底log()为常数,使用对数底2衍生@马丁ř

// double temp = (1 / (A + B*log(R_therm) + C*pow(log(R_therm),3)));
double temp = (1 / (A + B*log(R_therm)/log(2) + C*pow(log(R_therm)/log(2),3)));`

Sample implementation, that avoids an unnecessary slow pow() call. 示例实现,避免了不必要的缓慢pow()调用。

static const inv_ln2 = 1.4426950408889634073599246810019;
double ln2_R = log(R_therm)*inv_ln2;
double temp = 1.0 / (A + ln2_R*(B + C*ln2_R*ln2_R));

Yes, floating point arithmetic has limited precision on most arduinos. 是的,浮点算术在大多数arduino上的精度有限。

Have you considered using fixed precision? 您是否考虑过使用固定精度? If used correctly, this might give you better results. 如果正确使用,这可能会给您带来更好的结果。 The requirement for this is to have rather narrow parameters, however, and be careful about unit conversions. 对此的要求是具有相当窄的参数,并要小心单位转换。

An unsigned long on arduino is 4 bytes too, so it can contain numbers up to 2^32-1 . arduino上的unsigned long也是4个字节,因此它最多可以包含2^32-1数字。 If using fixed point, you might want to replace this 1/T by something like 100000/T , where the numerator constant and T have been scaled according to the desired precision. 如果使用定点,则可能要用类似于100000/T替换此1/T 100000/T ,其中分子常数和T已根据所需精度进行了缩放。

You will also need to keep a (mental or paper) model of the number of decimals each variable contains, in order to optimize the operation order not to lose precision. 您还需要保留每个变量包含的小数位数的(心理或纸质)模型,以优化操作顺序,而不会失去精度。

For the log2 function, I doubt it is available out of the box for integers. 对于log2函数,我怀疑它是否可以直接使用整数。 You could either cast the result or reimplement it . 您可以强制转换结果或重新实现它 There is plenty of ressources for this problem, even here on SO. 即使在SO上,也有很多资源可以解决此问题。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM