3 votes

Conversion d'un objet de type strict en chaîne de caractères en PHP 7

J'ai une fonction qui attend une chaîne de caractères comme paramètre d'entrée :

<?php
declare(strict_types = 1);

function testXml(string $xml) {
    echo "this is a string: " .$xml;
}

Maintenant, lorsque je donne un objet à cette fonction, je m'attends à ce qu'une erreur de type soit déclenchée. Mais ce n'est pas le cas, un objet de type SimpleXmlElement est silencieusement converti en une chaîne de caractères : https://3v4l.org/lQdaZ

Est-ce un bug ou une fonctionnalité ?

5voto

axiac Points 13906

Comme la documentation de l fonction magique __toString() explique :

En __toString() permet à une classe de décider comment elle va réagir lorsqu'elle est traitée comme une chaîne de caractères.

Parce que la classe SimpleXmlElement met en œuvre le __toString() la méthode magique, elle (la méthode) est invoquée chaque fois qu'une SimpleXmlElement est utilisé lorsqu'une chaîne de caractères est attendue. La valeur renvoyée par __toString() est utilisé à la place de l'objet.

Il est difficile de dire s'il s'agit d'une fonctionnalité ou d'un bogue. 1 . La fonction testXml() attend actuellement une chaîne de caractères comme argument et vous n'êtes pas satisfait du fait qu'il accepte silencieusement un fichier SimpleXmlElement à la place.

Si vous supprimez le type de son argument, l'appel à __toString() n'a plus lieu d'être et la valeur de l'élément $xml à l'intérieur de la fonction est l'argument SimpleXmlElement objet. L'appel à __toString() se produit dans le echo "this is a string: " .$xml; et il est très pratique que vous puissiez imprimer la valeur de $xml même si ce n'est pas une chaîne de caractères.

Si vous pensez que c'est un bug, alors echo (qui attend des chaînes de caractères comme arguments) devrait se plaindre du type de $xml et ne devrait pas l'imprimer. Pas si pratique, n'est-ce pas ?


1 Ce n'est pas un bug, c'est la façon dont le langage a évolué. __toString() a été introduit avant déclarations de type pour les types scalaires et, afin de ne pas casser le comportement existant, il est invoqué si c'est possible au lieu de déclencher une erreur sur le type incorrect de l'argument.

1voto

AndreKR Points 12941

C'est parce que vous passez la chaîne de caractères ( $simpleXml ) et non le SimpleXmlElement ( $xml ) à la fonction.

0voto

k0pernikus Points 2446

C'est une fonctionnalité que php appelle - si elle est définie - la __toString -méthode magique d'un objet :

Ce code nécessite php@7 :

<?php
class ClassImplementingToString
{
    public function __toString()
    {
        return "hello world";
    }
}

function foo(string $foo)
{
    echo $foo;
}

foo(new ClassImplementingToString());

produira un résultat : hello world

Exemple de bac à sable

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X