質問

I want to check an arbitrary (defined in data) set of rules expressed in text and eval() does the job nicely.

e.g. to define a rule to check that A and B are both valid:

Rule = "A and B"
print eval(Rule)

So how do I dynamically assign values to an arbitrary set of items?

I have a list of named Options and a list of Selections. Everthing in the Selections is considered valid (True) and everything in the Options, but not in the Selections is considered invalid (False).

So this code works but I don't like it because I am setting values within the local name space and I can't prevent an option name clashing with my local variables.

def CheckConstraints(self, Selections):
    'Validate the stored constraints'
    Good = True
    ## Undefined options default to False
    for i in self.Options:
        exec(i+" = False")  ## Bad - can I use setattr?
    ## Set defined Options to True
    for i in Selections:
        exec(i+" = True")  ## Bad - can I use setattr?
    for i in self.Constraints:
        if not eval( i ):
            Good = False
            print "Constraint Check Failure:", i, Selections
        else:
            print "Constraint Check OK:", i, Selections
    return Good

I have tried to use setattr, but it is not clear what setattr is setting and eval doesn't seem to be able to use the values set.

I'm on python 2.7x

Any suggestion welcome?

役に立ちましたか?

解決

eval can take a dictionary as its second argument which contains a new environment. Create a dictionary env and set your new variables within there, which ensures it won't clash with your local namespace:

def CheckConstraints(self, Selections):
    'Validate the stored constraints'
    Good = True
    env = {}
    ## Undefined options default to False
    for i in self.Options:
        env[i] = False
    ## Set defined Options to True
    for i in Selections:
        env[i] = True
    for i in self.Constraints:
        if not eval(i, env):
            Good = False
            print "Constraint Check Failure:", i, Selections
        else:
            print "Constraint Check OK:", i, Selections
    return Good
ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top