¿Por qué no se necesita la palabra clave ‘global’ para acceder a una variable global?

8 minutos de lectura

avatar de usuario
Nik

Según tengo entendido, Python tiene un espacio de nombres separado para las funciones, por lo que si quiero usar una variable global en una función, probablemente debería usar global.

Sin embargo, pude acceder a una variable global incluso sin global:

>>> sub = ['0', '0', '0', '0']
>>> def getJoin():
...     return '.'.join(sub)
...
>>> getJoin()
'0.0.0.0'

¿Me estoy perdiendo algo?

  • Creo que está confundido con php, que requiere el uso de la palabra clave global; los documentos de Python lo confirman; básicamente, si no está definido en el contexto local, se trata como global.

    – tobyodavies

    14 de enero de 2011 a las 16:15

  • Tenga cuidado con su redacción: Python no tiene un espacio de nombres separado para funciones (eso significaría que podría tener def foo(): ... y foo = ... al mismo tiempo). Crea un nuevo alcance para cada llamada de función. (Pero, ¿en qué se diferencia esto de cualquier otro idioma remotamente de alto nivel en el mundo?)

    usuario395760

    14/01/2011 a las 17:00


avatar de usuario
unode

la palabra clave global solo es útil para cambiar o crear variables globales en un contexto local, aunque la creación de variables globales rara vez se considera una buena solución.

def bob():
    me = "locally defined"    # Defined only in local context
    print(me)

bob()
print(me)     # Asking for a global variable

Lo anterior le dará:

locally defined
Traceback (most recent call last):
  File "file.py", line 9, in <module>
    print(me)
NameError: name 'me' is not defined

Mientras que si usas el global declaración, la variable estará disponible “fuera” del alcance de la función, convirtiéndose efectivamente en una variable global.

def bob():
    global me
    me = "locally defined"   # Defined locally but declared as global
    print(me)

bob()
print(me)     # Asking for a global variable

Así que el código anterior te dará:

locally defined
locally defined

Además, debido a la naturaleza de python, también podría usar global para declarar funciones, clases u otros objetos en un contexto local. Aunque lo desaconsejaría ya que causa pesadillas si algo sale mal o necesita depuración.

  • “global” en este contexto parece ser diferente de otros idiomas que consideran “global”. En Python, una referencia “global” todavía está dentro de los límites del módulo y debería ser referenciada desde fuera de ese módulo como “module.global_var” en lugar de simplemente “global_var” como cabría esperar.

    – jugo

    16 oct 2013 a las 5:30

  • @juice: en Python no existe el absoluto globals definido automáticamente en todos los espacios de nombres (afortunadamente). Como señaló correctamente, un global está vinculado a un espacio de nombres dentro de un módulo, sin embargo, se puede importar a otro módulo como from module import variable o import module.variable. En el primer caso, la importación haría accesible la variable como variable sin requerir referencia como module.. Si se considera global en el alcance del módulo dependerá de dónde se importe. Ver también nonlocal como una nueva palabra clave relacionada con el alcance en python 3.

    – unode

    16/10/2013 a las 17:07

  • ¿Podría explicar por qué las variables globales no son una buena solución? A menudo escucho esto, pero en mi proyecto actual parecen hacer exactamente lo que necesito que hagan. ¿Hay algo más siniestro en lo que no haya pensado?

    –Robin Newhouse

    18/10/2013 a las 13:05

  • @RobinNewhouse Hay algunas preguntas sobre SO que ya cubren ese tema y otras no SO artículos.

    – unode

    18/10/2013 a las 16:52

  • @phoenix tan global ¿Básicamente solo es útil para definir o iniciar variables globales desde un ámbito local?

    – chico mayor

    23 de mayo de 2021 a las 2:06


avatar de usuario
Ivo Wetzel

Si bien puede acceder a las variables globales sin la global palabra clave, si quieres modificarlas tienes que usar la global palabra clave. Por ejemplo:

foo = 1
def test():
    foo = 2 # new local foo

def blub():
    global foo
    foo = 3 # changes the value of the global foo

En tu caso, solo estás accediendo a la lista sub.

  • Con una advertencia: foo = 3 sin obras globales, pero foo se define de nuevo localmente en blub alcance de la función y no modifica la variable foo original. Esto fue bastante confuso para mí.

    – Chantyal

    19 de febrero de 2018 a las 14:40


  • @chhantyal si por obras quiere decir que no arroja un error, tiene razón, pero en el contexto de Ivo Wetzel no funcionaría según lo previsto. Hay usos para tal comportamiento, pero a menudo no es lo que quiere el programador.

    – democida

    11/04/2018 a las 22:31

  • ¿Alguien puede explicar el comentario de @chhantyal o @democidist? Cuando pruebo este código (con Python 3) y llamo blub()la foo fuera de la función se vincula a 3, como se esperaba.

    – Larry Engholm

    9 dic 2020 a las 23:43

  • @LarryEngholm, blub() funciona según lo previsto. Es test() eso no: hay nuevo, local foo creado y global foo conserva el valor.

    – Lehú

    15 de febrero de 2021 a las 22:04

  • tenga en cuenta que los valores dictados o los valores de la lista de índices SÍ cambian incluso sin la palabra clave global. stackoverflow.com/questions/14323817/…

    – Thomas Browne

    7 abr 2021 a las 11:44


avatar de usuario
pycruft

Esta es la diferencia entre acceder al nombre y Unión dentro de un alcance.

Si solo está buscando una variable para leer su valor, tiene acceso tanto al alcance global como al local.

Sin embargo, si asigna a una variable cuyo nombre no está en el ámbito local, está Unión ese nombre en este ámbito (y si ese nombre también existe como global, lo ocultará).

Si desea poder asignar al nombre global, debe decirle al analizador que use el nombre global en lugar de vincular un nuevo nombre local, que es lo que hace la palabra clave ‘global’.

La vinculación en cualquier lugar dentro de un bloque hace que el nombre en todas partes de ese bloque se vincule, lo que puede causar algunas consecuencias bastante extrañas (por ejemplo, UnboundLocalError que aparece repentinamente en el código que funcionaba anteriormente).

>>> a = 1
>>> def p():
    print(a) # accessing global scope, no binding going on
>>> def q():
    a = 3 # binding a name in local scope - hiding global
    print(a)
>>> def r():
    print(a) # fail - a is bound to local scope, but not assigned yet
    a = 4
>>> p()
1
>>> q()
3
>>> r()
Traceback (most recent call last):
  File "<pyshell#35>", line 1, in <module>
    r()
  File "<pyshell#32>", line 2, in r
    print(a) # fail - a is bound to local scope, but not assigned yet
UnboundLocalError: local variable 'a' referenced before assignment
>>> 

  • muy contrario a la intuición, difícil de creer que este es un código python válido

    – Por favor trabaje

    27 de abril de 2019 a las 23:43

avatar de usuario
tipo todo

Las otras respuestas responden a tu pregunta. Otra cosa importante que debe saber acerca de los nombres en Python es que son locales o globales según el ámbito.

Considere esto, por ejemplo:

value = 42

def doit():
    print value
    value = 0

doit()
print value

Probablemente puedas adivinar que el value = 0 declaración se asignará a una variable local y no afectará el valor de la misma variable declarada fuera de la doit() función. Puede que se sorprenda más al descubrir que el código anterior no se ejecutará. La declaración print value dentro de la función produce un UnboundLocalError.

La razón es que Python ha notado que, en otra parte de la función, asignas el nombre valuey también value no se declara en ninguna parte global. Eso lo convierte en una variable local. Pero cuando intenta imprimirlo, el nombre local aún no se ha definido. Python en este caso no retrocede a buscar el nombre como una variable global, como hacen algunos otros lenguajes. Esencialmente, no puede acceder a una variable global si ha definido una variable local del mismo nombre en cualquier sitio en la función.

avatar de usuario
usuario225312

Acceder a un nombre y asignar un nombre son diferentes. En su caso, solo está accediendo a un nombre.

Si asigna una variable dentro de una función, se supone que esa variable es local a menos que la declare global. En ausencia de eso, se supone que es global.

>>> x = 1         # global 
>>> def foo():
        print x       # accessing it, it is global

>>> foo()
1
>>> def foo():   
        x = 2        # local x
        print x 

>>> x            # global x
1
>>> foo()        # prints local x
2

avatar de usuario
martinas

  • Puede acceder a palabras clave globales sin palabra clave global
  • Para poder modificarlos, debe indicar explícitamente que la palabra clave es global. De lo contrario, la palabra clave se declarará en ámbito local.

Ejemplo:

words = [...] 

def contains (word): 
    global words             # <- not really needed
    return (word in words) 

def add (word): 
    global words             # must specify that we're working with a global keyword
    if word not in words: 
        words += [word]

avatar de usuario
Comunidad

Esto se explica bien en las preguntas frecuentes de Python

¿Cuáles son las reglas para las variables locales y globales en Python?

En Python, las variables a las que solo se hace referencia dentro de una función son implícitamente globales. Si a una variable se le asigna un valor en cualquier lugar dentro del cuerpo de la función, se asume que es local a menos que se declare explícitamente como global.

Aunque un poco sorprendente al principio, la consideración de un momento explica esto. Por un lado, exigir global para las variables asignadas proporciona una barrera contra los efectos secundarios no deseados. Por otro lado, si global se requería para todas las referencias globales, estaría usando global todo el tiempo. Tendrías que declarar como global cada referencia a una función integrada oa un componente de un módulo importado. Este desorden anularía la utilidad de la global declaración para identificar los efectos secundarios.

https://docs.python.org/3/faq/programming.html#cuáles-son-las-reglas-para-variables-locales-y-globales-en-python

¿Ha sido útil esta solución?

Esta web utiliza cookies propias y de terceros para su correcto funcionamiento y para fines analíticos y para mostrarte publicidad relacionada con sus preferencias en base a un perfil elaborado a partir de tus hábitos de navegación. Al hacer clic en el botón Aceptar, acepta el uso de estas tecnologías y el procesamiento de tus datos para estos propósitos. Configurar y más información
Privacidad