views:

36750

answers:

8

A global variable created in one function cannot be used in another function directly. Instead I need to store the global variable in a local variable of the function which needs its access. Am I correct? Why is it so?

+3  A: 

I could ask just as properly why you're asking. Why do you believe the global is a better solution. Global shared state is a widely known source of common problems. Keep adding functions that manipulate global data and you'll quickly loose track what what might be causing some unexpected problem with it. Python's many design decisions are artifacts of understanding what keeps software understandable and crafting a language that encourages that wisdom.

ironfroggy
Agree. It's often bad form to use globals. Make sure you have a valid reason. If not your probably better off restructuring your code, using a class for example.
monkut
+1: Globals are simply a bad policy. They make functions have confusing (and unexpected) side-effects. They break idempotency.
S.Lott
+7  A: 

You may want to explore the notion of namespaces. In Python, the module is the natural place for global data:

Each module has its own private symbol table, which is used as the global symbol table by all functions defined in the module. Thus, the author of a module can use global variables in the module without worrying about accidental clashes with a user’s global variables. On the other hand, if you know what you are doing you can touch a module’s global variables with the same notation used to refer to its functions, modname.itemname.

A specific use of global-in-a-module is described here - how-do-i-share-global-variables-across-modules:

The canonical way to share information across modules within a single program is to create a special configuration module (often called config or cfg). Just import the configuration module in all modules of your application; the module then becomes available as a global name. Because there is only one instance of each module, any changes made to the module object get reflected everywhere. For example:

File: config.py

x = 0   # Default value of the 'x' configuration setting

File: mod.py

import config
config.x = 1

File: main.py

import config
import mod
print config.x
gimel
+43  A: 

You can use a global variable in other functions by declaring it as global in each function that modifies it:

globvar = 0

def set_globvar_to_one():
    global globvar    # Needed to modify global copy of globvar
    globvar = 1

def print_globvar():
    print globvar     # No need for global declaration to read value of globvar

set_globvar_to_one()
print_globvar()       # Prints 1

I imagine the reason for it is that, since global variables are so dangerous, Python wants to make sure that you really know that's what you're playing with by explicitly requiring the global keyword.

See other answers if you want to share a global variable across modules.

Paul Stephenson
This doesn't quite work that way in my Python 2.6. For some reason, the global declaration needs to be in the function where you interact with globvar, even if you have declared it as global elsewhere
inspectorG4dget
@inspectorG4dget: I think that is what I was trying to say. The `global` declaration is in `set_globvar_to_one` because that is where you interact with `globvar` -- but if, like `print_globvar`, a function is only reading the value of `globvar`, not writing it, then you don't need a special `global` declaration to access the global variable's value. If your behaviour is different could you add some code to illustrate it?
Paul Stephenson
+1. Very illustrative yet concise answer! Exactly what I, as Python noob, needed.
Jonik
+3  A: 

If you want to refer to global variable in a function, you can use global keyword to declare which variables are global. You don't have to use it in all cases (as someone here incorrectly claims) - if the name referenced in an expression cannot be found in local scope or scopes in the functions in which this function is defined, it is looked up among global variables. However, if you assign to a new variable not declared as global in the function, it is implicitly declared as local, and it can overshadow any existing global variable with the same name.

Also, global variables are useful, contrary to some OOP zealots who claim otherwise - especially for smaller scripts, where OOP is overkill.

J S
+19  A: 

If I'm understanding your situation correctly, what you're seeing is the result of how Python handles local (function) and global (module) namespaces.

Say you've got a module like this:

----- sample.py -----
myGlobal = 5

def func1():
    myGlobal = 42

def func2():
    print myGlobal

func1()
func2()

You might expecting this to print 42, but instead it prints 5. As has already been mentioned, if you add a 'global' declaration to func1(), then func2() will print 42.

def func1():
    global myGlobal
    myGlobal = 42

What's going on here is that Python assumes that any name that is assigned to, anywhere within a function, is local to that function unless explicitly told otherwise. If it is only reading from a name, and the name doesn't exist locally, it will try to look up the name in any containing scopes (e.g. the module's global scope).

When you assign 42 to the name myGlobal, therefore, Python creates a local variable that shadows the global variable of the same name. That local goes out of scope and is garbage-collected when func1() returns; meanwhile, func2() can never see anything other than the (unmodified) global name. Note that this namespace decision happens at compile time, not at runtime -- if you were read the value of myGlobal inside func1() before you assign to it, you'd get an UnboundLocalError, because Python has already decided that it must be a local variable but it has not had any value associated with it yet. But by using the 'global' statement, you tell Python that it should look elsewhere for the name instead of assigning to it locally.

(I believe that this behavior originated largely through an optimization of local namespaces -- without this behavior, Python's VM would need to perform at least three name lookups each time a new name is assigned to inside a function (to ensure that the name didn't already exist at module/builtin level), which would significantly slow down a very common operation.)

Jeff Shannon
A: 

You're not actually storing the global in a local variable, just creating a local reference to the same object that your original global reference refers to. Remember that pretty much everything in Python is a name referring to an object, and nothing gets copied in usual operation.

If you didn't have to explicitly specify when an identifier was to refer to a predefined global, then you'd presumably have to explicitly specify when an identifier is a new local instead (eg. with something like the 'var' command seen in Javascript). Since locals are more common than globals in any serious and non-trivial system, Python's system makes more sense in most cases.

You could have a language which attempted to guess, using a global if it existed or creating a local if it didn't. However, that would be very error-prone. For example, importing another module could inadvertently introduce a global by that name, changing the behaviour of your program.

Kylotan
+1  A: 

this really helped, thx a lot guyz :D

sids
A: 

I have a question similar to this. I didn't want to start a new question when mine is almost the same. I have a module where say I have something like this:

from sqlite3 import *

conn = NONE
curs = NONE
ect = NONE

def createConnection(path):
   global conn,curs,ect
   conn = connect(path)
   curs = conn.cursor()
   ect = curs.execute

It works fine for when I'm using the module directly but when I import it into another module, the 'global' keyword doesn't work anymore when I run the function. At least in my tests in IDLE.

Thanks

Isaiah