De quelque chose comme ça:
print(get_indentation_level())
print(get_indentation_level())
print(get_indentation_level())
J'aimerais obtenir quelque chose comme ceci:
1
2
3
Le code peut-il se lire de cette manière?
Tout ce que je veux, c'est que la sortie des parties les plus imbriquées du code soit plus imbriquée. De la même manière que cela rend le code plus facile à lire, cela rendrait la sortie plus facile à lire.
Bien sûr, je pourrais l'implémenter manuellement, en utilisant par exemple .format()
, mais ce que j'avais à l'esprit était une fonction d'impression personnalisée qui serait print(i*' ' + string)
où se i
trouve le niveau d'indentation. Ce serait un moyen rapide de rendre une sortie lisible sur mon terminal.
Existe-t-il une meilleure façon de faire cela qui évite un formatage manuel fastidieux?
python
reflection
metaprogramming
indentation
tokenize
Fab von Bellingshausen
la source
la source
get_indentation_level()
déclaration dans votre code. Vous pouvez tout aussi bien faireprint(3)
ou n'importe quoi directement. Ce qui pourrait être plus intéressant, c'est le niveau actuel d'imbrication sur la pile d'appels de fonction.depth
paramètre et en lui ajoutant la valeur appropriée si nécessaire lorsque vous le transmettez à d'autres fonctions. L'imbrication de votre code n'est pas susceptible de correspondre proprement à l'indentation que vous souhaitez sortir de votre sortie.Réponses:
Si vous voulez une indentation en termes de niveau d'imbrication plutôt que d'espaces et de tabulations, les choses se compliquent. Par exemple, dans le code suivant:
l'appel à
get_nesting_level
est en fait imbriqué d'un niveau de profondeur, malgré le fait qu'il n'y ait pas d'espace blanc au début sur la ligne de l'get_nesting_level
appel. En attendant, dans le code suivant:l'appel à
get_nesting_level
est imbriqué à zéro niveaux de profondeur, malgré la présence d'espaces blancs de premier plan sur sa ligne.Dans le code suivant:
les deux appels à
get_nesting_level
sont à des niveaux d'imbrication différents, malgré le fait que le premier espace blanc soit identique.Dans le code suivant:
est-ce que ce sont des niveaux zéro imbriqués ou un? En termes de
INDENT
et deDEDENT
jetons dans la grammaire formelle, il n'y a aucun niveau, mais vous pourriez ne pas ressentir la même chose.Si vous voulez faire cela, vous allez devoir tokeniser l'ensemble du fichier jusqu'au point de l'appel et compter
INDENT
etDEDENT
tokens. Letokenize
module serait très utile pour une telle fonction:la source
get_nesting_level()
est appelé dans cet appel de fonction - il retourne le niveau d'imbrication dans cette fonction. Pourrait-il être réécrit pour revenir au niveau d'imbrication «global»?while
etwith
, ce serait faisable, mais ce n'est pas ce que vous avez demandé, et changer la question pour demander quelque chose de différent à ce stade serait une mauvaise idée.linecache
module pour des trucs comme celui-ci cependant - il est utilisé pour imprimer des traces, et peut gérer les modules importés à partir de fichiers zip et d'autres astuces d'importation étranges)linecache
peut être bon pour réduire la quantité d'E / S de fichier (et merci de me le rappeler), mais si je commençais à optimiser cela, je serais dérangé par la façon dont nous re-tokenisons de manière redondante le même fichier pour les répétitions du même appel, ou pour plusieurs sites d'appel dans le même fichier. Il y a un certain nombre de façons dont nous pourrions optimiser cela aussi, mais je ne sais pas à quel point je veux vraiment régler et protéger ce truc fou.Ouais, c'est certainement possible, voici un exemple de travail:
la source
print('{Space}'*get_indentation_level(), x)
Vous pouvez utiliser
sys.current_frame.f_lineno
pour obtenir le numéro de ligne. Ensuite, pour trouver le nombre de niveau d'indentation, vous devez trouver la ligne précédente avec une indentation nulle, puis soustraire le numéro de ligne actuel du numéro de cette ligne, vous obtiendrez le numéro d'indentation:Démo:
Si vous voulez le numéro du niveau d'indentation basé sur les lignes précédentes,
:
vous pouvez le faire avec un peu de changement:Démo:
Et comme réponse alternative, voici une fonction pour obtenir le nombre d'indentation (espace blanc):
la source
:
jusqu'à ce que nous rencontrions la ligne sans indentation, vérifiez l'édition!{3:4, \n 2:get_ind_num()}
Pour résoudre le «vrai» problème qui mène à votre question, vous pouvez implémenter un gestionnaire de contexte qui garde la trace du niveau d'indentation et fait correspondre la
with
structure de bloc dans le code aux niveaux d'indentation de la sortie. De cette façon, l'indentation du code reflète toujours l'indentation de sortie sans trop coupler les deux. Il est toujours possible de refactoriser le code en différentes fonctions et d'avoir d'autres indentations basées sur une structure de code qui ne joue pas avec l'indentation de sortie.Production:
la source
la source