views:

58

answers:

4
class AlphaBetaAgent(MultiAgentSearchAgent):

  def action(self,gamestate):
    self.alpha= -9999
    self.beta = 9999

    def abc(gamestate, depth, alpha, beta):


    def bvc(gamestate, depth, alpha, beta):


   return abc(gamestate, 0, alpha, beta)

I am calling the getAction function which itself calling the abc funct and abc function calling the bvc funct. The functions abc and bvc are working in recursive way. I need to modify the values of alpha and beta as per the situation demands so I made them local. BUt it is not letting me to do that. Error occurs

Error occurs:- global name 'alpha' is not defined

A: 

To use a global variable you have to do something like:

global alpha
alpha = -9999

townsean
Shilpa
+2  A: 

In Python, global variables must be declared outside of the function. Then, any function can read that variable without any problems, but if a function wants to write to it it has to declare it global. Example:

def fun1():
     print a
def fun2():
     a = 3
def fun3():
     global a
     a = 3
a = 0
fun1() # <- Will work
fun2() # <- Will raise exception
fun3() # <- Will work
Stealth-
name 'beta' is a function parameter and declared global - a error occurs like this when I apply your method
Shilpa
I'm not sure exactly what your problem is. If you want to use local variables in a function and manipulate them without worrying about global variables, that works fine, normally. I'm not sure quite what you are doing by declaring a function inside of a function. Have you tried classes instead?
Stealth-
there is a class in which a function Getaction is defined and in getAction fnction, i made 2 more functions
Shilpa
+2  A: 

Use a class. Storing state & behaviour is what classes are for.

Tim McNamara
+1: And avoid global variables. They are often a terrible design blunder.
S.Lott
+1  A: 

If you want functions like abc and bvc to use common variables, you generally want to define an object for them to be methods of, like so:

class ActionState(object):
   def abc(self, gamestate, depth):
       self.alpha = -9999
       self.beta = 9999
   def bvc(self, gamestate, depth):
       self.alpha = -9999
       self.beta = 99999

def action(self, gamestate):
   state = ActionState()
   state.abc(gamestate, 0)

Alternatively, if you really want to, you can enclose a mutable object like a dict around to hold your data:

def action(self, gamestate):
    actionstate = { 'alpha': 0, 'beta': 0 }

    def abc(gamestate, depth):
        actionstate['alpha'] = -9999
        actionstate['beta'] = 9999

    def bvc(gamestate, depth):
        actionstate['alpha'] = -9999
        actionstate['beta'] = 9999

    abc(gamestate, 0)

Note that the actionstate parameter isn't passed here -- it's inherited from the enclosing scope. You can pass it explicity instead if you want, in which case abc and bvc no longer need to be defined inside of action. The reason this works and your example doesn't is that Python binds any primitive identifier lexically to the most-local function where it is assigned. So when you assign to alpha in abc, Python defines an alpha as local to abc, not action. I believe the only way to get a closure in Python is not to assign to the enclosed variable within the inner function.

Walter Mundt
the abc and bvc functions are defined in the function getAction. So where do I exactly define my alpha and beta....I cant use self.alpha??
Shilpa
`alpha` and `beta` must be defined as components of a dictionary or object which is created above the definitions of `abc` and `bvc`. That way you can assign to them without creating a second version in a more-local scope. See added explanation at end of answer.
Walter Mundt
Also, why can't you use `self.alpha`?
Walter Mundt
check my edited question.
Shilpa
When I use self.alpha and self.beta , error occurs. Im not writing the function def abc(self,gamestate,alpha, beta)- it is def abc(gamestate, depth,alpha , beta)
Shilpa
See my first example code -- if you use an object, you do have to change the method signature of `abc` and `bvc`. You add `self` at the beginning and also drop the alpha and beta parameters, because those are kept inside of `self`. Then you call `abc` and `bvc` as methods instead of functions, so they get their implicit self parameters, as also demonstrated in my example. Note that just because a function has a particular signature in some pseudocode you found somewhere, it doesn't necessarily have to look like that when you write it, as long as the same job gets done!
Walter Mundt
In your example, def getaction is single function. BUt in my case, It has 2 functions def abc and def bvc. ABC and BVC are part of function getAction. I tried to do what you said, but a error occurs like" AlphaBetaAgent instance has no attribute 'abc'
Shilpa
I moved abc and bvc out of `getAction` deliberately. For it to work they have to be part of the class. Why do they have to be part of `getAction` if all the shared state they need is moved into instance variables of the class?
Walter Mundt