在函数内部动态创建变量
我想从字典中的函数内部创建变量。
可以说我有一本字典
bar = {'a': 1, 'b': 2, 'c': 3}
和功能
def foo(): pass
我想要做的是创建内部函数" foo"变量,每个字典项名称的名称和值作为字典项值
所以最后应该类似于
def foo(): a = 1 b = 2 c = 3
有可能吗?如果确实如此,该怎么做?
解决方案
你为什么要做这样的事情?除非我们实际上对函数内部的变量进行任何操作,否则仅分配几个变量然后将其丢弃的函数与def foo()不能区分开:pass(优化器在生成完全相同的字节码时是合理的)。
如果我们还想动态添加使用值的代码,则可以使用exec来做到这一点(尽管除非这确实是用户输入的代码,否则几乎肯定会有更好的方法来执行所需的操作)。例如:
some_code = ' return a+b+c' exec "def foo():\n " + '\n '.join('%s = %s' for k,v in bar.items()) + '\n' + some_code
(请注意,代码必须缩进相同的级别。)
另一方面,如果我们想将这些值实际分配给函数对象(因此我们可以执行foo.a并得到1个示例代码没有执行的注释),则可以通过以下方式执行此操作
for key, val in bar.items(): setattr(foo, key, val)
问题不清楚。
如果要在不运行foo时"设置"所述变量,则不能,不能。还没有框架对象可用于"设置"局部变量。
如果要在函数主体中执行此操作,则不应该这样做(请查看python文档中的locals())。
但是,我们可以执行foo .__ dict __。update(bar),然后甚至可以从函数内部访问这些变量,如foo.a,foo.b和foo.c。问题是:为什么要这样做?为什么一门课不适合目的?
谢谢大家,我明白了。我不应该这样做。但是,如果古玩是我想做的,就是在Django的view函数中以某种方式缩短行数。我有很多字段的表单,而不是接收以下形式的每个字段:
first_name = form.cleaned_data['first_name'] last_name = form.cleaned_data['last_name'] ..
我正在考虑采用我的表单类的每个属性名称并对其进行循环。像这样:
for name in ProfileRegistration.base_fields.__dict__['keyOrder']: # and here the variables that i tried to assign
根据评论,也许我们真正想要的是类似束对象的东西:
class Bunch(object): def __init__(self, **kwargs): self.__dict__.update(kwargs) b=Bunch(**form.cleaned_data) print b.first_name, b.last_name
(**语法是因为在情况下不使用Bunch类型的对象,就像Bunch(foo = 12,bar ='blah')一样,但为了与正常用法保持一致,我将其保留了)
这确实需要" b"。前缀来访问变量,但是如果我们考虑一下,这并不是一件坏事。请考虑一下,如果有人设计了一个POST请求来覆盖我们不希望被覆盖的变量,那么它将很容易产生崩溃和DOS攻击,并且很容易引入更严重的安全漏洞。