oscat.lib > oscat.lib fuer Step 7
Arithmetik doppelter Genauigkeit
Langnese:
Hallo,
hier nun endlich die benötigten Infos.
die Programmierung mit Real-Zahlen sieht so aus:
i := (i + 1) MOD Zyklen;
MW := MW + (Rohwert - buffer) / INT_TO_REAL(Zyklen);
buffer := Rohwert;
wobei diese Befehle nur einmal pro Bausteinaufruf bearbeitet werden.
Dann habe ich das auf REAL2 umgesetzt:
i:= (i + 1) MOD Zyklen;
MW_Double:= R2_ADD2(X:= MW_Double, Y:= R2_MUL(X:= (R2_ADD2(X:= Rohwert_Double, Y:= R2_MUL(X:= buffer, Y:= -1))), Y:= Eins_Zyklen));
buffer:= Rohwert_Double;
. Das Ergebnis ist in beiden fällen identisch, auch der *.R1 Anteil bleibt 0.
Die "fehlerfreie" Variante wäre:
FOR k:= 0 TO 3599 DO
STD_MW_neu:= STD_MW_neu + STD_buffer[k] / 3600;
END_FOR;
und das dauert zu lange.
Inzwischen habe ich mit den Funktionen von REAL2 etwas experimentiert und habe ein kleines Testprojekt aufgesetzt. In der Doku steht:
"Möchte man bis zu Mehreren Mwh (Megawattstunden) an Gesamtverbrauch Aufsummieren und dabei eine kleinste Leistung von 1mW (Milliwatt) im Abstand von 10ms Messen und berücksichtigen, so benötigt man eine Auflösung von 3.6 * 10^7 (entspricht 10MWs) und dabei würde man 1 * 10^-5 Ws aufaddieren wollen.
Um dies zu bewerkstelligen benötigt man eine Auflösung von 12 Stellen."
Also habe ich folgendes programmiert:
CALL "R2_SET"
X :=1.0 E-5
RET_VAL:="Test".Eingang1
CALL "R2_SET"
X :=3.6 E7
RET_VAL:="Test".Eingang2
CALL "R2_ADD2"
X :="Test".Ergebnis
Y :="Test".Eingang2
RET_VAL:="Test".Ergebnis
und habe das im OB1 zyklisch mit 1 ms laufen lassen. Das läuft jetzt schon 48 Stunden. Dann hätte eigentlich der Ausgangswert sich um 172.800.000, also sichtbar verändern müssen. Aber der ausgang steht immer noch bei RX=3.6 E7 und R1=0.
Was habe ich dabei falsch gemacht ?
Danke und Gruß
dalbi:
Hallo,
was soll "Test".Eingang1 machen der ist in Deiner berechnung ja gar nicht verwendet?
Der Typ REAL2 ist folgender maßen definiert:
*.R1 : REAL Grobteil der Doppelzahl
*.RX : REAL Feinteil der Doppelzahl
R2_SET beschreibt lediglich *.RX mit dem Wert von X *.R1 ist immer 0.0, somit hast Du an Deinen Ausgang "Test".Ergebnis.RX immer die 3.6 E7 stehen "Test".Ergebnis.R1 bleibt natürlich 0.
R2_ADD2 addiert X.R1 mit Y.R1 und X.RX mit Y.RX.
Gruss Daniel
dalbi:
Halt das ist natürlich Käse
"immer die 3.6 E7 stehen" -> im ersten Zyklus im zweiten sind es dann 3.6E7 + 3.6E7 = 7.2E7 ...
Gruss Daniel
Langnese:
Hallo,
sorry, da ist mir ein Tippfehler unterlaufen, aber nur hier im posting.
Programmiert ist:
CALL "R2_SET"
X :=MD50
RET_VAL:="Test".Eingang1
CALL "R2_SET"
X :=MD54
RET_VAL:="Test".Eingang2
CALL "R2_ADD2"
X :="Test".Ergebnis
Y :="Test".Eingang2
RET_VAL:="Test".Ergebnis
wobei MD50:= 3.6 E07 und MD54:= 1,0E-05 gesetzt ist. Damit Test.Ergebnis überhaupt initialisert ist, habe ich zum starten den Eingang X von "R2_ADD" einmalig mit Test.Eingang1 beschaltet, so daß Test.Ergebnis mit 3,6E07 initialisiert war.
Ich hoffe, so wird es klarer.
Gruß Peter
dalbi:
Hallo,
R2_ADD ist nicht gleich R2_ADD2 nimm mal R2_ADD.
Gruss Daniel
Navigation
[0] Themen-Index
[#] Nächste Seite
[*] Vorherige Sete
Zur normalen Ansicht wechseln