Énumérer ou de la liste de toutes les variables dans un programme de [votre langue préférée ici]
Un ami m'a demandé la semaine dernière comment énumérer ou de la liste de toutes les variables à l'intérieur d'un programme/fonction/etc. pour les fins de débogage (essentiellement obtenir un aperçu de tout ce que vous pouvez voir quelles sont les variables définie, ou si elles sont définies à tous). J'ai regardé un peu autour et a trouvé un relativement bon moyen pour Python:
#!/usr/bin/python toto1 = "Bonjour le monde" foo2 = "barre" foo3 = {"1":"un", "2":"b"} foo4 = "1+1" pour le nom de dir(): mavaleur = eval(nom) nom en caractères d'imprimerie, "est", type(nom), "et est égal à ", mavaleur
qui va afficher quelque chose comme:
__les builtins__ <type 'str'>, et est égal à <module " __builtin__' (built-in)> __doc__ <type 'str'>, et est égal à Aucun __fichier__ <type 'str'>, et est égal à ./foo.py ___ nom_ <type 'str'>, et est égal à __principaux__ toto1 est <type 'str'>, et est égal Bonjour tout le monde foo2 est <type 'str'>, et est égal à la barre foo3 est <type 'str'>, et est égal à {'1': 'a', '2': 'b'} foo4 est <type 'str'>, et est égal à 1+1
J'ai trouvé jusqu'à présent une partie en PHP (avec l'aimable autorisation de texte du lien), mais il ne répertorie toutes les variables et leurs types, pas le contenu:
<?php //créer un peu de variables $bar = 'foo'; $foo = "bar"; //création d'un nouvel objet array $arrayObj = new ArrayObject(get_defined_vars()); //boucle sur le tableau de l'objet et de l'écho des variables et des valeurs for($iterator = $arrayObj->getIterator(); $iterator->valide(); $iterator->next()) { echo $iterator->key() . '=> ' . $iterator->current() . '<br />'; } ?>
Donc je l'ai mis pour vous: comment avez-vous la liste de toutes les variables et leur contenu dans votre langue préférée?
Édition par VonC: je vous propose cette question suit l'esprit d'un petit "code-défi".
Si vous n'êtes pas d'accord, il suffit d'éditer et de supprimer le tag et le lien.
- En python, je venais de l'utilisation de variables locales/globales plutôt que de le dir/eval vous montrer ci-dessus. Voir ci-dessous.
- En PHP il peut également être fait beaucoup plus facile, voir ma réponse.
- C'est un hack de une question, car il n'est pas question sur une question spécifique, il est dit "allons voir ce que vous pouvez faire dans votre langue?". C'est une question de discussion, car il n'y a pas une seule bonne réponse. Par conséquent, il devrait probablement être supprimé, mais au moins marqué wiki de la communauté. C'est plus un post sur le forum.
- Je suis en désaccord, mon plan est de choisir la solution la plus élégante dans l'ensemble et de le définir comme la réponse et presto. Je suppose que si j'avais demandé à l'un de ces pour chaque question qui serait considérée plus comme une "bonne" cause, mais il est intéressant de noter que les méthodes utilisées dans les différentes langues se chevauchent souvent avec d'autres langues (c'est à dire utiliser le débogueur/etc.).
- Je pensais exactement la même chose. Les réponses sont en effet utiles, mais la question n'est pas SOI-qualifiés. Je suis d'accord qu'il devrait aller CW.
- great post. J'avais besoin de cela pour obtenir une liste de variables que j'ai défini dans un module. avec un test de " pas de nom.startswith('__')'(à l'aide de python) cela fait des miracles pour moi. Merci beaucoup
- Soupir. Ne devrait pas être à la fois 1) fermée pour être trop large parce qu'il est en plusieurs langues, et 2) la "double redirection" pour des questions d'une langue unique.
- Je serai d'accord, l'utilisation de ce comme un dupe de la cible spécifique des questions du langage est fondamentalement dire "à chaque question unique sur la façon d'obtenir une liste de variables doit être fermé".
Vous devez vous connecter pour publier un commentaire.
En python, en utilisant les habitants qui retourne un dictionnaire contenant toutes les liaisons, ainsi, d'éviter eval:
C'est ce qu'il pourrait ressembler à Ruby:
qui sera de sortie
Cependant, n'avez-vous pas dire à la sortie de la type d'objet que l'références à des variables à la place du type utilisé pour représenter la variable d'identification? OIE, le type de
foo3
devrait êtreHash
(oudict
) au lieu deString
, droit? Dans ce cas, le code seraitet le résultat est
instance_variable_get(instance_variables[0])
En php, vous pourriez faire ceci:
En Lua fondamentaux de la structure de données est la table et même l'environnement mondial _G est un tableau. Oui, une simple énumération fera l'affaire.
IPython:
Vous pourrait aussi recommander Spyder à votre ami qui montre que les variables à peu près comme Matlab ne et fournit une interface utilisateur graphique pour la, ligne par ligne, de débogage.
Bash:
Avertissement: n'est Pas mon préféré de la langue!
env
pour trouver les valeurs ne sont pas exportés.Un récursives, PHP one-liner:
Tout d'abord, je serais tout simplement utiliser un débogueur ;-p
Visual Studio, par exemple, a des "Habitants" et "Montre" de windows qui affiche toutes les variables, etc vous le souhaitez, totalement extensible à n'importe quel niveau.
En C# vous ne pouvez pas vraiment obtenir à la méthode des variables très facilement (et ils sont nombreux à être retiré par le compilateur) - mais vous pouvez accéder aux champs etc via la réflexion:
Perl. Ne gère pas les
my
les habitants, et ne filtre pas certains inutile de références, mais tout dans l'étendue d'un package peut être vu.Matlab:
En java, le problème serait similaire à C#, mais en plus le mode verbose (je sais, JE SAIS 😉 Java est verbeux... vous avez fait clair que déjà 😉 )
Vous pouvez accéder aux champs d'objet par le biais de Réfection, mais vous ne pouvez pas accéder facilement à la méthode des variables locales. Donc la suite n'est pas pour l'analyse statique de code, mais pour le runtime debugging seulement.
AccessController
est inutile dans une application autonome (bien,setAccessible
est pas nécessaire pour accéder à vos propres champs de toute façon) ou leif
déclaration de différencier les deux cas qui peuvent être traités de la même manière lors de la suppression de l'obsolètetoString()
appel:System.out.println(aField.getName() + ": " + res);
fonctionne, indépendamment de savoir sires
estnull
ou pas. Et il n'y a pas besoin de répandre le code sur plusieurs méthodes, soit...Dans le langage R
et à supprimer tous les objets de la mémoire de travail
En REBOL, toutes les variables vivre à l'intérieur d'un contexte de type
object!
. Il y a un contexte mondial, et chaque fonction a sa propre implicite du contexte local. Vous pouvez créer de nouveaux contextes explicitement par la création d'une nouvelleobject!
(ou à l'aide de lacontext
fonction). Ceci est différent de langues traditionnelles parce que les variables (appelés "mots" dans REBOL) effectuer une référence à leur contexte avec eux, même quand ils ont quitté le "champ" dans lequel elles ont été définies.Donc, la ligne de fond est que, dans un contexte donné, nous pouvons lister les variables qu'il définit. Nous allons utiliser Ladislav Mecir de
contexte-mots?
fonction.Maintenant, nous pouvons liste de tous les mots définis dans le contexte mondial. (Il y a un beaucoup d'entre eux.)
Nous pouvons aussi écrire une fonction qui affiche les variables qu'il définit.
Ce que nous ne peut pas faire en REBOL, pour autant que je sais, c'est marcher le contexte de l'arbre, bien que l'interprète semble être en mesure de le faire parfaitement bien quand il décide de la façon de lier les mots de leur contexte. Je pense que c'est parce que le contexte de l'arbre (c'est à dire, le champ d'application) peut avoir une "forme" à la fois un mot est lié, mais tout à fait une autre, à la fois, c'est évaluée.
Rapide et sale JavaScript solution si vous avez installé FireBug (ou un autre navigateur de la console.le journal). Si vous ne le faites pas, vous aurez à changer de console.journal du document.écrire, et exécuter dans à un script en ligne à la fin de votre . Changement MAX_DEPTH pour combien de niveaux de récursivité vous voulez (attention!).
Common Lisp:
Aussi de montrer tous liés valeurs:
C'est une longue liste, et pas particulièrement utile. Je voudrais vraiment utiliser le débogueur intégré.
Voici une idée pour oo-langues.
D'abord, vous besoin de quelque chose comme toString() en Java pour imprimer des contenus valables.
La deuxième, vous devez vous limiter à un objet de la hiérarchie. Dans le constructeur de la racine de l'objet (comme Tout dans Eiffel), votre inscription de l'instance lors de la création dans une sorte de liste globale. Lors de la destruction, vous désinscrire (assurez-vous d'utiliser certains de structure de données qui permet d'effectuer rapidement insérer /recherche /suppression). Tout moment pendant l'exécution du programme, vous pouvez marcher à travers cette structure de données et d'imprimer tous les objets enregistrés là.
En raison de sa structure, Eiffel est peut-être très bon pour cette fin. D'autres Langues ont des problèmes avec des objets qui ne sont pas définis par l'utilisateur (par exemple, le jdk-classes). En Java, il pourrait être possible de créer votre propre Objet-classe à l'aide de certains open-source du jdk.