Mit Readings rechnen - Readings umrechnen

Begonnen von kblc, 06 Mai 2017, 12:07:21

Vorheriges Thema - Nächstes Thema

kblc

Hallo,

ich bin im Moment drüber herauszufinden, wie man mit Readings rechnen kann.
Folgendes Projekt:
Ich habe einen Sensor in FHEM (Marke: Eigenbau). Der liefert einen Wert, der falsch ist. Der Wert, den er liefert ist: 511. Der Wert den er liefern soll ist: 22.5°C. Also Raumtemperatur, bzw. 22,5.
Nun würde ich gerne ein Reading haben, mit dem berechneten Wert 22,5. Entweder 511-488,5  oder  511*22,7. Das  muss ich erst testen. Aber für mich interessant wäre zu wissen, wie ich die Sache richtig berechne?

Ich habe in Readings "reading" mit dem Wert "511".
Nun habe ich in Commandref, anderen Forenbeiträgen und wiki nachgelesen, und finde aber kein passendes funktionierendes Tool.
Folgenden Code habe ich:
attr Firmata_ANALOG userReadings Temperatur integral /22
Das Ergebnis ist aber falsch.

Kann mir jemand wieder mal auf die Sprünge helfen?


Vielen Dank

Kai
SPS, Arduino, Controllino, Sensortechnik, Elektronik

DeeSPe

userReadings würde ich auch nehmen.
Du kannst darin auch Perl Code benutzen und somit machen was Du willst.

Gruß
Dan
MAINTAINER: 22_HOMEMODE, 98_Hyperion, 98_FileLogConvert, 98_serviced

Als kleine Unterstützung für meine Programmierungen könnt ihr mir gerne einen Kaffee spendieren: https://buymeacoff.ee/DeeSPe

CoolTux

Wäre es nicht besser das Übel bei der Wurzel zu packen und schon am/beim Sensor die Umrechnung zu mache ?
Du musst nicht wissen wie es geht! Du musst nur wissen wo es steht, wie es geht.
Support me to buy new test hardware for development: https://www.paypal.com/paypalme/MOldenburg
My FHEM Git: https://git.cooltux.net/FHEM/
Das TuxNet Wiki:
https://www.cooltux.net

kblc

Danke für die schnellen Antworten. Das ist echt super.

Zitat von: CoolTux am 06 Mai 2017, 13:52:57
Wäre es nicht besser das Übel bei der Wurzel zu packen und schon am/beim Sensor die Umrechnung zu mache ?
Ich bin erst am Anfang meiner könnerischen Leistung. Es tut mir ehrlich leid, aber ich muss ganz ehrlich schreiben: "keine Ahnung".
Der Sensor ist über Firmata (Arduino) am Raspberry Pi und hat folgenden code:

define Firmata_ANALOG FRM_AD 14
attr Firmata_ANALOG IODev FIRMATA
attr Firmata_ANALOG alias Eingang_Pin_14
attr Firmata_ANALOG event-min-interval 5
attr Firmata_ANALOG fp_Ansicht01 50,200,8,
attr Firmata_ANALOG group Firmata
attr Firmata_ANALOG room Firmata
attr Firmata_ANALOG stateFormat reading
attr Firmata_ANALOG userReadings Temperatur integral {ReadingsVal("Eingang_Pin_14","reading"/22}


Es ist ein PT1000 der hängt jetzt direkt am Arduino, ähnlich nach dem Prinzip:
http://funduino.de/nr-9-temperatur-messen

Daher wollte ich mal versuchen den Sensor einfach umzurechnen, da er in meinem Temperaturspektrum relativ gleichmäßig ansteigt. Die kleine Abweichung ist dann auch kein Problem.


Danke nochmal

Kai
SPS, Arduino, Controllino, Sensortechnik, Elektronik

CoolTux

Ich würde versuchen das ganze schon innerhalb meines Sketch korrekt zu rechnen. Wie und wo kann ich aber auch nicht sagen. Sinn ergibt es aber.
Du musst nicht wissen wie es geht! Du musst nur wissen wo es steht, wie es geht.
Support me to buy new test hardware for development: https://www.paypal.com/paypalme/MOldenburg
My FHEM Git: https://git.cooltux.net/FHEM/
Das TuxNet Wiki:
https://www.cooltux.net

kblc

Danke, das ist schon mal eine sehr beruhigende Aussage, dann muss es ja bald klappen.
Solange ich nicht auf dem blöden Holzweg herumtappe. :)

Schönes Wochenende noch.

Kai
SPS, Arduino, Controllino, Sensortechnik, Elektronik

Thorsten Pferdekaemper


attr Firmata_ANALOG userReadings Temperatur {ReadingsVal("Eingang_Pin_14","reading",0) / 22}

Oder?
Gruß,
   Thorsten
FUIP

devien

Hm, ich frage mich hier gerade warum in aller Welt nimmt man die Rechenkapazität von einem Arduino und der Wirtsmachine auf der FHEM läuft und rechnet dann damit 1+1 ?
oder mit anderen Worten, kann man wenn man schon "messen" will nicht auch "ordentlich berechnen umwandeln?

Ein PT1000 hat eine fest vorgegebene Kennlinie mit präzisen Werten. daraus folgt, wenn ich eine Spannung von z.B.5V am Eingang eines Spannungsteilers habe und als Messergebniss einen präzisen Wert zwischen 0 und 1023 dann ist der Messwert gleich einer bestimmten Spannung.

Nehme ich dann diese Spannung und setze sie in folgende Formel RTD Resistance = Vout x R / (Vcc - Vout) rearranged for: Vout = Vcc x RTD / (RTD + R) (ja ist abgekupfert von https://learn.openenergymonitor.org/electricity-monitoring/temperature/rtd-temperature-sensing?redirected=true)ein so erhalte ich ?
richtig, den exakten Widerstandswert.
Letzten noch vergleichen mit einer Wertliste und schon habe ich die Temperatur.

Klar ist das etwas umfassender als Pi * Daumen / Fensterkreuz2 aber wozu sonst mit solcher Hardware erst arbeiten?
FHEM + UniPi + Arduino = gute Lösung

devien

ich habe da mal einen Anfang
defmod temp_01 FRM_AD 14
attr temp_01 IODev Arduino
attr temp_01 event-min-interval 60
attr temp_01 fp_Solar 58,508,2,Solar_temp_01
attr temp_01 room Arduino
attr temp_01 stateFormat reading
attr temp_01 userReadings Resistance {(5*ReadingsVal("temp_01","reading",0) /1024)*1000/(5-(5*ReadingsVal("temp_01","reading",0) /1024))}
attr Solar_temp_01 verbose 5


als Richtwert habe ich einen PT1000 mit einem 1KOhm Wiederstand als Spannungsteiler genutzt. Der Arduino hängt an stabilen 5V was auch die Referrenzspannung ist und am Spannungsteiler anliegt.

Der wert liegt bei aktuell knappen 40 Grad auf 1150

Fehlt nur noch die Umsetzung des Widerstandswertes "Resistance" auf die Temperatur.
Eine recht brauchbare obgleich nicht sehr detailierte Liste finet sich unter http://delta-r.de/de/aktuelles/wissen/pt1000-widerstandstabelle

Kann jemand einen Tipp geben wie man die Temperatur nun herrausbekommt?
FHEM + UniPi + Arduino = gute Lösung

Thorsten Pferdekaemper

Hi,
ich habe eine ähnliche Problemstellung mal vor ein paar Jahren gehabt. Ich habe die Tabelle (Temperatur/Widerstand) genommen und habe mir für jeden Zeile den Wert ausgerechnet, den der Arduino-Eingang tatsächlich liefert. Mit dieser Tabelle, (eingeschränkt auf den tatsächlich vorkommenden Wertebereicht) habe ich dann eine Stückweise lineare Interpolation gemacht.
Das ganze konnte ich dann ein bisschen optimieren, indem man manche Werte weglässt.
Gruß,
   Thorsten
FUIP

devien

Zitat von: Thorsten Pferdekaemper am 24 Juni 2017, 19:49:06
Mit dieser Tabelle, (eingeschränkt auf den tatsächlich vorkommenden Wertebereicht) habe ich dann eine Stückweise lineare Interpolation gemacht.
die Tabelle existiert ja bereits, kannst du als code / codebeispiel darlegen wie du die interploration interpretiert hast oder dies heute umsetzen würdest?
FHEM + UniPi + Arduino = gute Lösung

Thorsten Pferdekaemper

Hi,
ich hab das nur in "Arduinisch", also C++:

int multiMap(int val, int* _in, int* _out, uint8_t size)
{

  // decreasing _in Array?
  boolean decIn = ( _in[0] > _in[size-1] );

  // take care the value is within range
  // val = constrain(val, _in[0], _in[size-1]);
  if(decIn){
    if (val >= _in[0]) return _out[0];
    if (val <= _in[size-1]) return _out[size-1];
  }
  else{
    if (val <= _in[0]) return _out[0];
    if (val >= _in[size-1]) return _out[size-1];
  }
  // search right interval
  uint8_t pos = 1;  // _in[0] allready tested
  if(decIn){
    while(val < _in[pos]) pos++;
  }
  else{
    while(val > _in[pos]) pos++;
  };
  // this will handle all exact "points" in the _in array
  if (val == _in[pos]) return _out[pos];

  // interpolate in the right segment for the rest
  return map(val, _in[pos-1], _in[pos], _out[pos-1], _out[pos]);
}

Aufrufbeispiel:

// Temperaturkurve Aussentemperatur
int temperaturesAT[] = {
  -20, -4, 14, 30, 50 };
int readingsAT[] = {
  452, 487, 524, 555, 591
};
byte tlSizeAT = 5;
return multiMap(raw,readingsAT,temperaturesAT,tlSizeAT);

Das Prinzip ist ziemlich einfach: Zuerst sucht man, in welchem Intervall der Wert liegt und dann interpoliert man linear innerhalb des Intervalls.
Gruß,
   Thorsten

FUIP