2010-08-16 7 views
1

Je cherche une fonction comme sprintf(), sauf qu'avec sprintf() vous liez les valeurs par ordre d'arguments, je veux quelque chose où je peux lier des variables par leur nom. Donc, si j'avais la chaîne "Hello $name! We're please to have you visit, $name!", vous pourriez passer un tableau ou quelque chose et obtenir la chaîne résultante.liaison nommée des variables dans les chaînes?

Quelque chose comme les instructions PDO, mais seulement pour les chaînes de caractères, pas les requêtes de base de données. Que puis-je utiliser?

Répondre

3

preg_replace/e ou preg_replace_callback est votre meilleur pari

$vars = array('name' => 'Joe', 'age' => 25); 
    $str = "@name is @age years old"; 
    echo preg_replace('/@(\w+)/e', '$vars["$1"]', $str); 
+0

Stereofrog - le nom d'utilisateur awesomest avec les réponses awesomest! – user151841

0

Peut-être que vous pourriez utiliser anonymous functions, de sorte que les variables libres sont liées en tant que paramètres dans la fonction anonyme, ce qui renvoie une chaîne avec les valeurs remplissant les variables libres. Cela fonctionnerait bien en conjonction avec la fonction extract à l'intérieur d'une fermeture, dans lequel les clés de votre tableau deviennent des variables réelles dans une portée locale nécessaire pour évaluer les variables référencées dans la chaîne de format.

Ou il y a probablement une version relativement simple en utilisant eval (ce qui est juste une illustration, pas de code testé):

function named_printf ($format_string, $values) { 
    extract($values); 
    $result = $format_string; 
    eval('$result = "'.$format_string.'";'); 
    return $result; 
} 

echo named_printf ('Hello $msg', array('msg'=>'World')); 

mécanismes de contrôle de la portée de PHP sont un peu effrayant, de sorte que vous pouvez vérifier que cette ne va pas couler des variables dans la portée partout. Cela vaudrait également la peine de recevoir des commentaires.

+0

'eval' est pas une solution, il est un problème. –

+0

D'accord. C'est pourquoi j'ai suggéré d'utiliser une fermeture en première instance, puis j'ai dit qu'il y avait une "version relativement simple" en utilisant eval, si OP voulait une solution généralisée à la manière de printf. Il est acceptable d'utiliser eval si vous implémentez réellement des fonctionnalités génériques au niveau du système. – Gian

+0

"Il est acceptable d'utiliser eval si vous implémentez réellement des fonctionnalités génériques au niveau du système.", Je ne suis pas d'accord, il y a presque * toujours * un meilleur moyen. 'eval' est difficile à maintenir et mauvais pour la performance et la sécurité. –

2

PHP a intégré un support pour l'évaluation des variables à l'intérieur des chaînes entre guillemets. Bien que vous ne puissiez pas vous passer un tableau, vous pouvez penser à la portée de la variable en cours comme entrée pour le générateur de chaînes "function".

$name = "Kendall Hopkins"; 
print "Hello {$name}!"; //Hello Kendall Hopkins! 

http://www.php.net/manual/en/language.types.string.php#language.types.string.parsing

EDIT:

Une solution plus souple pourrait être de résumé sur le code dans une fermeture. Cela ne dépend pas de eval et sera probablement plus rapide.

$hello_two = function (array $params) { 
    extract($params); 
    return "Hello $name1 and $name2!"; 
} 

//Hello User and Kendall 
$hello_two(array("var1" => "User", "var2" => "Kendall")); 
+0

Oui, je sais, mais je veux une fonction qui fait cela afin que je puisse réutiliser ma chaîne de template à plusieurs endroits. En d'autres termes, je ne veux pas que les variables soient liées au moment de l'écriture. Utiliser cette fonctionnalité php rend la chaîne unique et je ne peux pas la réutiliser. – user151841

+0

@ user151841 Jetez un oeil à mon édition. –

+0

Cela semble exiger une fermeture séparée par chaîne de format. Est-ce vraiment ce qu'on demandait? – Gian

Questions connexes