Utilise la source, Luke
Comme toujours, la réponse se trouve dans la source. PHP utilise les deux fonctions suivantes en interne pour effectuer les opérations d'incrémentation et de décrémentation :
ZEND_API int increment_function(zval *op1)
ZEND_API int decrement_function(zval *op1)
Ces opérations modifient le op1
en fonction de son type ( NULL
est un type) ; à l'intérieur increment_function()
vous pouvez voir la branche suivante dans le code :
case IS_NULL:
ZVAL_LONG(op1, 1);
break;
Le code ci-dessus change le type de op1
en un nombre et fixe sa valeur à 1
.
Inversement, decrement_function()
n'offre pas une telle branche et donc le action par défaut sera effectuée :
default:
return FAILURE;
L'exécution de ce code ne produira pas d'échec observable, car les valeurs de retour sont absorbées par la Zend VM, mais la variable n'est pas non plus mise à jour.
Ce n'est pas un bug(tm)
Vous serez peut-être surpris d'apprendre que ce comportement, y compris celui des valeurs booléennes, est en réalité documenté :
Note : Les opérateurs d'incrémentation/décrémentation n'affectent pas les valeurs booléennes. Décrémenter NULL
n'a pas d'effet non plus, mais les incrémenter a pour effet de 1
.
En ce qui concerne les booléens :
$a = true;
var_dump($a--); // true
$a = false;
var_dump($a++); // false
En ce qui concerne les cordes :
$letter = 'A';
var_dump(++$letter); // B
var_dump(--$letter); // B