PHP kleiner als (hat die Funktion von kleiner/gleich)

Hallo,

ich habe hier ein seltsames Phänomen mit einem einfachen Vergleich von zwei Variablen:

if($current_room['Ist-Temperatur'] < $current_room['Soll-Temperatur']) 

wird true auch wenn Beispielsweise beider Variablen 21.0 als Wert haben. Erst wenn die Ist-Temperatur auf 21.1 steigt, liefert der Vergleich false.

Ich habe die Ist-Temperatur bereits gerundet:

round($variable, 1);

erhalte jedoch das gleiche Ergebnis. Die Werte sind richtig; ich lasse diese noch ins Log-Schreiben:

Ist [b](21.5)[/b] kleiner Soll ([b]21.5[/b] ;zu kalt)

Kann mir hier jemand auf die Sprünge helfen dieses, eigentlich triviale, Problem zu lösen?

Grüße Johannes

Was für ein Variablentyp ist denn


var_dump($current_room['Ist-Temperatur']);

?

<= schon probiert :slight_smile:

Hallo Fonzo,

echo "VARDUMP Ist-Temperatur: " . var_dump($current_room['Ist-Temperatur']) . PHP_EOL;
	echo "VARDUMP Soll-Temperatur: " . var_dump($current_room['Soll-Temperatur']) . PHP_EOL;

meldet

float(20.7)
VARDUMP Ist-Temperatur: 
float(20.7)
VARDUMP Soll-Temperatur:

Sollte doch passen, oder?

JensNRW, was genau hast du „schon probiert“ :smiley:

du musst deine Abfrage erweitern

20,7 ist nicht kleiner als 20,7 somit false

du fragst den WERT ob er kleiner ist ,was er nicht ist,

deswegen

if($current_room[‚Ist-Temperatur‘] < $current_room[‚Soll-Temperatur‘])

gegen

if($current_room[‚Ist-Temperatur‘] <= $current_room[‚Soll-Temperatur‘])

so ist der Wert kleiner oder gleich = true

Hallo Jens,

leider ist ja genau das Problem, dass

If 20,7 < 20,7

true zurückgibt. Und das ist ja schlichtweg falsch.

Letzendlich vergleiche ich hier Soll und Ist-Wert und wenn der Ist-Wert kleiner als der Soll-Wert ist, ist das Thermostat aktiv. Leider ist das Thermostat solange aktiv, bis der Sollwert über dem Ist-Wert liegt.

Grüße.

Völlig korrekt, dir fehlen Klammer ;).

If (20,7 < 20,7)

Hier mal zum Nachschlagen.
PHP lernen – PHP lernen leicht gemacht

Gesendet von iPhone mit Tapatalk

Der letzte Vergleich war wohl nur symbolisch-anschaulich gemeint. Im tatsächlichen Code in Beitrag #1 ist die Klammer vorhanden.

mach mal:

if(intval($current_room['Ist-Temperatur']) < intval($current_room['Soll-Temperatur']))

Wenn dein 27,6 Beispiel stimmt, dann lieber float(). Das ist vermutlich auch das Problem beim Vergleich, du vergleichst zwei Strings. Eine Zahl im PHP hat einen Punkt als Dezimaltrennzeichen.

Vielleicht hilft dieser Link
http://www.php.net/manual/en/language.types.float.php

Da wird auch gesagt, wie mn float Werte vergleichen kann

Laut dem Output hat er schon 2 Floats, aber der Vergleich entspricht nicht immer der Auswertung, die geht bis x Stellen hinter dem KOmma (9 glaube ich), deswegen die Umwandlung in int, dann sollte es gehen…

schon probiert?

Danke für die hilfreichen Tipps.

Aussagekräftig ist übrigens wirklich nur der erste Beitrag. Alles andere waren nur Veranschaulichungen.

Um das Problem mit Nachkommastellen zu eliminieren, hatte ich bereits auf eine Stelle nach dem Komma gerundet.

Was soll ich sagen: Ohne eine Änderung meinerseits läuft es nun.

Die letzte Änderung war die Rundung des Ist-Werts auf eine Stelle nach dem Komma, die jedoch nicht geholfen hat.
Zusätzlich habe ich den Server in der Zwischenzeit neu gestartet.

Da viele Werte (u.a. der Ist-Wert) aus einem eigenen per require eingebundenen Script kommen vermute ich, das dieses Script evtl. gecached wird und dies durch den Neustart umgangen wurde?

Grüße.

halt, Kommando zurück :smiley:

Es funktioniert wohl nur teilweise. Mit verschiedenen Soll/Ist-Werten funktioniert es weiterhin nicht.

Hier nochmals der Code:

if($current_room['Ist-Temperatur'] < $current_room['Soll-Temperatur']) {
				echo "Ist (" .  $current_room['Ist-Temperatur'] . ") kleiner Soll (" . $current_room['Soll-Temperatur'] . " ;zu kalt)" . PHP_EOL;
					echo abs($current_room['Ist-Temperatur']);
					if($current_room['Heizen aktiv'] != 1) {
						if ($current_room['Lüften aktiv'] != 1) {
							echo "Heizen nicht aktiv" . PHP_EOL;
							echo "Setze Heizen aktiv auf true" . PHP_EOL;
							echo "aktiviere Thermostat" . PHP_EOL;
							EIB_Switch($current_room['Raumthermostat ID'], true);
							SetValueBoolean($current_room['Heizen aktiv ID'], true);
						}
					}
					else {
					echo "Heizen bereits aktiv" . PHP_EOL;
										}
			        
				}
echo abs($current_room['Ist-Temperatur']);

wird ausgegeben, auch wenn beide Temperaturen beispielsweise 20,1 sind.

hagbard235: Eine Umwandlung in Int wird mir hier nur sehr bedingt etwas helfen, oder? Die Nachkommastellen gehen ja komplett verloren, oder?

Aber ja, wenn ich intval verweden, triggert die Abfrage erst, wenn Soll 21 Grad ist und Ist beispielsweise 20,3.

Grüße.

Moin,

ich vermute mal, dass deine Floating Point Variablen nicht die exakten Werte haben. Dies ist ein leidiges Problem, wenn man nicht gewohnt ist, mit solchen REAL Zahlen, Double Precision Werten usw umzugehen. Im HM Forum findest du hier https://homematic-forum.de/forum/viewtopic.php?f=26&t=36623&start=680 reichlich Stoff zu dem Thema.

Du musst eine Differenz berechnen und davon abhängig machen wie du reagieren willst. Anbei ein Beispiel wo ungleiche Float Werte dann als identisch ermittelt werden.

<?
$current_room_ist = 20.1;
$current_room_soll = 20.1;

if ($current_room_ist < $current_room_soll)
{
	echo "dies darf so nicht der Fall sein 
";
}
else
{
	echo "die Werte sind nicht kleiner und das ist auch gut so 
";
}


$current_room_ist = 20.99999981;
$current_room_soll = 20.99999980;

if ($current_room_ist < $current_room_soll)
{
	echo "dies darf so nicht der Fall sein 
";
}
else
{
	echo "die Werte sind nicht kleiner und das ist auch gut so 
";
}

// Gleichheit testen obwohl ungleich als FP Variablen
$abs = abs($current_room_ist - $current_room_soll);
echo "Differenz " . $abs . "
";
$epsilon = 0.0001;

if ($abs < $epsilon)
{
	echo "die Differenz ist kleiner als epsilon  ==> die Werte sind gleich obowhl dies in der Floating Point Darstellung nicht der Fall ist 
";
}
?>

Vielleicht hilft dir dies ja weiter :wink:

Gruß
Hans

Wenn du Nachkomma-Genauigkeit für deinen Vergleich willst, machst du halt *10 für 1 Nachkomma-Stelle und *100 für 2… und dann den int-Vergleich

So würde ich es auch machen.:slight_smile:

Es sieht so aus als wenn es nun endlich funktionieren würde.

if(intval($current_room['Ist-Temperatur'] * 10) < intval($current_room['Soll-Temperatur'] * 10))

brachte den gewünschten Erfolg.

Vielen Dank an alle für die Hilfe!