la portée des variables python

voix
2

J'ai commencé à en apprendre davantage sur python et est en train de lire à travers un script écrit par quelqu'un d'autre. J'ai remarqué que globals sont dispersés dans le script (et je ne l'aime pas) .. En outre, j'ai aussi remarqué que quand j'ai le code comme celui-ci

def some_function():
    foo.some_method()
    # some other code

if __name__ == '__main__' :
    foo = Some_Object()

    some_function()

même si je ne passe pas foo dans une_fonction (), mais une_fonction est encore capable de manipuler foo (??!). Je ne pas tout à fait comme ça même si elle est un peu similaire à la fermeture Javascript (?). Je voudrais savoir s'il est possible d'arrêter une_fonction () d'accéder foo si foo n'est pas transmis comme un argument de fonction? Ou c'est la façon préférée en python ??! (J'utilise Python 2.5 sous ubuntu hardy pour le moment)

Créé 27/08/2009 à 03:41
source utilisateur
Dans d'autres langues...                            


3 réponses

voix
4

Ce scénario a des problèmes très sérieux avec le style et l' organisation - par exemple, si quelqu'un importe ce qu'ils doivent en quelque sorte divine le fait qu'ils doivent mettre thescript.fooà une instance de Some_Objectavant d' appeler some_function... yeurgh -!)

Il est regrettable que vous ayez à apprendre Python à partir d'un script mal écrit, mais je ne suis pas sûr que je comprends votre question. Portée des variables en Python est la population locale (y compris les arguments), nonlocals (c.-à-habitants des fonctions environnantes, pour les fonctions imbriquées), globals builtins.

Est - ce que vous voulez arrêter l' accès à globals? some_function.func_globalsest en lecture seule, mais vous pouvez faire une nouvelle fonction avec GLOBALS vide:

import new
f=new.function(some_function.func_code, {})

appelant maintenant f()sera donné une exception NameError: global name 'foo' is not defined. Vous pouvez définir ce retour dans le module avec le nom some_function, ou même le faire systématiquement par un décorateur, par exemple:

def noglobal(f):
    return new.function(f.func_code, {})
...
@noglobal
def some_function(): ...

cela garantira l'exception se produit chaque fois que l' some_functionon appelle. Je ne suis pas clair sur ce que vous attendez avantages à tirer de cela, cependant. Peut - être que vous pouvez préciser ...?

Créé 27/08/2009 à 04:11
source utilisateur

voix
2

Pour autant que je sache, le seul moyen d'arrêter some_functiond'accéder fooest d'éliminer la foovariable d' some_functionétendue de, peut - être comme:

tmp = foo
del foo
some_function()
foo = tmp

Bien sûr, cela va planter votre code (actuel) depuis foon'existe pas dans le cadre de some_functionplus.

En Python, les variables sont recherchées localement, dans la portée jusqu'à ce que le monde, et enfin sont recherchés Encastrements.

Une autre option pourrait être:

with some_object as foo:
    some_function()

Mais alors, vous devrez déclarer au moins some_object.__exit__, peut - être some_object.__enter__aussi bien. Le résultat final est que vous contrôlez ce qui fooest dans le cadre de some_function.

Plus d' explications sur le « par » déclaration ici .

Créé 27/08/2009 à 03:53
source utilisateur

voix
1

En python, quelque chose comme foon'est pas une valeur, il est un nom . Lorsque vous essayez d' y accéder, python essaie de trouver la valeur qui lui est associée (comme le déréférencement d' un pointeur). Elle le fait en examinant d' abord dans la portée locale (la fonction), travaille ensuite son chemin vers l' extérieur jusqu'à ce qu'il atteigne la portée du module (c. -à- global), et enfin builtins, jusqu'à ce qu'il trouve quelque chose correspondant au nom.

Cela fait quelque chose comme ce travail:

def foo():
    bar()

def bar():
    pass

Malgré le fait que barn'existe pas lorsque vous avez défini foo, la fonction fonctionnera parce que vous avez défini plus tard bardans un champ qui entoure foo.

Exactement la même chose qui se passe dans le code que vous publiez, il est juste que fooest la sortie Some_Object(), et non une définition de fonction.

Comme Alex a dit, le fait que vous pouvez écrire du code comme cela ne signifie pas que vous devriez .

Créé 27/08/2009 à 05:06
source utilisateur

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more