(int) vs. is_numeric() - nur positive Zahlen

Descartes

Erfahrenes Mitglied
Hallo!

In mehreren Threads hier habe ich gesehen, dass eine Prüfung auf Ganzzahlen oft mit einem vorangestellten (integer) $variable gemacht wird.

Vorteil des expliziten umwandeln der Variable in einen Integerwert ist also gegenüber is_numeric() , dass is_numeric() auch Kommazahlen zuläßt, richtig?

Integer umfasst aber auch negative Ganzzahlen. Läßt es sich erreichen, dass nur positive Zahlen akzeptiert werden?

abs() bildet zwar den absoluten Betrag, aber ich möchte erreichen, dass id=-2 nicht in id=2 umgewandelt wird, sondern -2 als ungültig zurückgewiesen wird. Nach Möglichkeit ohne irgendwelche Ersetzungsfunktionen, die ich vorschalten müßte.

Einfaches Bsp.:
Code:
if($_GET[(int) $id]){
Lösche Eintrag mit $id aus der DB
}

Verständlicherweise möchte ich nicht den Eintrag mit $id=2 löschen, wenn $id=-2 übergeben wurde, sondern ich will, dass gar nichts passiert.

Grüße

Martin
 
Wie Du schon richtig sagst laesst is_numeric() auch Fliesskommazahlen zu. is_int() hingegen scheint oft problematisch zu sein, vor allem mit uebergebenen Werten.
Man koennte aber is_int() durch eine eigene kurze Funktion ersetzen die wie folgt aussieht und auch mit uebergebenen Werten klarkommen duerfte.
PHP:
function my_is_int($x)
{
 return ($x==intval($x));
}

Nachtrag: Um noch etwas mehr auf das Thema einzugehen koennte man dies nun noch etwas erweitern, und zwar so:
PHP:
function my_is_positive_int($x)
{
 return ($x==abs(intval($x)));
}
 
Hallo!

Das ist genau das was ich gesucht habe.

Wenn ich dass richtig verstehe:

1. Funktion: Ich übergebe den Wert $x, der jeden beliebigen Typ haben kann. $x wird in einen Integerwert konvertiert und wenn er dann immernoch gleich dem Eingabewert $x ist ($x also bspw. keine Fließkommazahl war), dann gib true zurück, andernfalls false.

2. Funktion: Wie 1., nur dass der eingegebene Wert gleich dem Betrag des konvertierten $x sein muss, also nicht negativ sein darf.

Grüße

Martin
 
Genau richtig verstanden.
Man koennte das auch etwas komplexer gestalten, aber der Vergleich liefert ja direkt zurueck was man auch aus der Funktion zurueckgeben will und somit kann man das ganze halt gleich in einer Zeile loesen.
 
Ich hab grad mal was rumprobiert und herausgefunden, dass es aus irgendeinem Grund ein Problem dabei gibt.
Mit diesem Code hab ich getestet:
PHP:
<?php
function is_id($value)
{
  return ($value==abs(intval($value)));
}
echo '5: '.is_id(5)."\r\n";
echo '5.5: '.is_id(5.5)."\r\n";
echo '-5: '.is_id(-5)."\r\n";
echo '"5": '.is_id('"5"')."\r\n";
echo 's5: '.is_id('s5')."\r\n";
echo '5s: '.is_id('5s')."\r\n";
?>
Ausgabe:
5: 1
5.5:
-5:
"5": 1
s5: 1
5s: 1
Wie Du siehst wird aus unerfindlichen Gruenden bei s5 und 5s true zurueckgeliefert.

Entsprechend sollte also in die Funktion auch noch is_numeric() verbaut werden.
Der Code sieht dann so aus:
PHP:
<?php
function is_id($value)
{
  return ((is_numeric($value)) && ($value==abs(intval($value))));
}
echo '5: '.is_id(5)."\r\n";
echo '5.5: '.is_id(5.5)."\r\n";
echo '-5: '.is_id(-5)."\r\n";
echo '"5": '.is_id('"5"')."\r\n";
echo 's5: '.is_id('s5')."\r\n";
echo '5s: '.is_id('5s')."\r\n";
?>
Dadurch ist gibt es dann auch die erwartete Ausgabe:
5: 1
5.5:
-5:
"5":
s5:
5s:

Wenn man == durch === ersetzt hat dies in der ersten Variante zwar augenscheinlich den gewuenschten Effekt, jedoch wird dabei (in beiden Varianten) auch fuer uebergebene Werte (ich hab hier mit aus der Shell uebergebenen Werten mittels $argv getestet) false ausgegeben, auch wenn diese eigentlich true ergeben sollten.
 
Hallo!

Bei === wird doch die Gleichheit des Typs mitgeprüft, wenn ich also eine String an die Funktion übergebe und mit === gegen den nach Int konvertierten prüfe, dann muss das doch zwangsläufig auf ein false hinauslaufen, oder?

Aber wenn ein Einbau von is_numeric die Lösung bringt ... :p

Grüße

Martin
 
Richtig, und Uebergabewerte sind glaub ich immer Strings, was ja auch der Grund ist, dass is_int() daran scheitert.
Aber in der 2. Variante ist die Funktion, nach meinem aktuellen Test zur Zeit aussieht, funktionsfaehig und ein ganz guter Ersatz fuer is_int(). Und wenn man auch negative Integer haben will muss man nur abs() entfernen. ;)
 
Die is_numeric()-Funktion ist zur Prüfung von positiven Ganzzahlen so ungeeignet wie fast keine andere. Denn diese Funktion prüft lediglich, ob der übergebene Wert einem numerischen äquivalent ist. Denn – oh Wunder – 1, -1, 1.0, -.123 und 123e-45 sind alle numerisch!
 
In der von mir gezeigten Funktion dient is_numeric() auch nur dem Zweck zu dem es gemacht wurde, zu pruefen ob es sich um einen numerischen Wert handelt.
Und das ja auch nur weil in der Funktion ohne is_numeric() merkwuerdigerweise auch s5 und 5s als positive Ganzzahlen gewertet werden, obwohl abs(intval('s5')) 0 zurueckgibt (und abs(intval('5s')) gibt 5 zurueck) und der Vergleich 's5'==0 (bzw. '5s'==5) eigentlich false ergeben sollte.
Dementsprechend hab ich fuer den Return-Wert noch is_numeric() verknuepft um sicherzustellen, dass es sich um einen numerischen Wert handelt der geprueft wird.
 
Zurück