2010-01-10 7 views
3

Est-il possible de créer une variable variable pointant vers un tableau ou vers des objets imbriqués? Les doc php disent spécifiquement que vous ne pouvez pas pointer vers SuperGlobals mais ce n'est pas clair (pour moi au moins) si cela s'applique aux tableaux en général.Variables variables pointant vers des tableaux ou des objets imbriqués

Voici mon essai sur le tableau var var.

 // Array Example 
    $arrayTest = array('value0', 'value1'); 
    ${arrayVarTest} = 'arrayTest[1]'; 
    // This returns the correct 'value1' 
    echo $arrayTest[1]; 
    // This returns null 
    echo ${$arrayVarTest}; 

Voici un code simple pour montrer ce que je veux dire par l'objet var var.

 ${OBJVarVar} = 'classObj->obj'; 
    // This should return the values of $classObj->obj but it will return null 
    var_dump(${$OBJVarVar});  

Est-ce que je manque quelque chose d'évident ici?

+0

Mis à jour ma réponse pour inclure le problème d'index de tableau aussi, je vous ai mal lu et j'ai pensé que vous aviez cela sous contrôle! – johnnyArt

+0

Si la variable-variable est la réponse, vous posez probablement une mauvaise question. Pourquoi ne pas simplement utiliser l'assignation par référence? –

Répondre

5

approche élément Array:

  • Extrait nom du tableau de la chaîne et le magasin dans $arrayName.
  • Extrait l'index de la chaîne et la stocke dans $arrayIndex.
  • Analysez-les correctement plutôt que dans son ensemble.

Le code:

$arrayTest = array('value0', 'value1'); 
$variableArrayElement = 'arrayTest[1]'; 
$arrayName = substr($variableArrayElement,0,strpos($variableArrayElement,'[')); 
$arrayIndex = preg_replace('/[^\d\s]/', '',$variableArrayElement); 

// This returns the correct 'value1' 
echo ${$arrayName}[$arrayIndex]; 

Propriétés de l'objet approche:

  • Explode la chaîne contenant la classe et la propriété que vous souhaitez accéder par son delimiter (->).
  • Affectez ces deux variables à $class et $property.
  • Parse séparément au lieu de l'ensemble sur var_dump()

Le code:

$variableObjectProperty = "classObj->obj"; 
list($class,$property) = explode("->",$variableObjectProperty); 

// This now return the values of $classObj->obj 
var_dump(${$class}->{$property});  

Il fonctionne!

+0

Merci! Exactement ce que j'essayais d'accomplir. A travaillé parfaitement. – Bookworm

0

En echo $arrayTest[1];, le nom de la variable est $arrayTest avec un indice de tableau de 1 et non $arrayTest[1]. Les crochets sont des "mots-clés" PHP. Idem avec la notation de méthode et l'opérateur ->. Donc vous devrez vous séparer.

// bla[1] 
$arr = 'bla'; 
$idx = 1; 
echo $arr[$idx]; 

// foo->bar 
$obj = 'foo'; 
$method = 'bar'; 
echo $obj->$method; 

Qu'est-ce que vous voulez faire ressemble plus à l'évaluation du code PHP (eval()). Mais rappelez-vous: eval est le mal. ;-)

0

Non, vous ne pouvez pas faire cela. Vous ne pouvez le faire qu'avec des noms de variables, d'objets et de fonctions.

Exemple:

$objvar = 'classObj'; 
var_dump(${$OBJVarVar}->var); 

alternatives peuvent être via eval() ou en faisant pré-traitement.

$arrayTest = array('value0', 'value1'); 
$arrayVarTest = 'arrayTest[1]'; 

echo eval('return $'.$arrayVarTest.';'); 
eval('echo $'.$arrayVarTest.';'); 

qui est si vous êtes très sûr de ce qui va être l'entrée.

Par prétraitement:

function varvar($str){ 
    if(strpos($str,'->') !== false){ 
    $parts = explode('->',$str); 
    global ${$parts[0]}; 
    return $parts[0]->$parts[1]; 
    }elseif(strpos($str,'[') !== false && strpos($str,']') !== false){ 
    $parts = explode('[',$str); 
    global ${$parts[0]}; 
    $parts[1] = substr($parts[1],0,strlen($parts[1])-1); 
    return ${$parts[0]}[$parts[1]]; 
    }else{ 
    return false; 
    } 
} 

$arrayTest = array('value0', 'value1'); 
$test = 'arrayTest[1]'; 
echo varvar($test); 
1

Utilisez = & pour assigner par référence:

$arrayTest = array('value0', 'value1'); 
$arrayVarTest = &$arrayTest[1]; 

$arrayTest[1] = 'newvalue1'; // to test if it's really passed by reference 

print $arrayVarTest; 
+0

asker ne pose pas de questions sur le référencement. – mauris

+0

@mauris: peut-être que trouver cette réponse alors que googler m'a donné la solution que je cherchais;) – hugsbrugs

Questions connexes