我想做这样的事情:
property = 'name'
value = Thing()
class A:
setattr(A, property, value)
other_thing = 'normal attribute'
def __init__(self, etc)
#etc..........
Run Code Online (Sandbox Code Playgroud)
但我似乎无法找到对类的引用,以便setattr像在类定义中分配变量一样工作.我怎样才能做到这一点?
有没有办法让我的Android应用程序检索和设置文件的扩展用户属性?有没有办法java.nio.file.Files在Android 上使用?有没有办法使用setfattr,并 getfattr从我的Dalvik应用程序?我知道android使用ext4文件系统,所以我想它应该是可能的.有什么建议?
我知道你不能调用object.__setattr__没有继承的对象object,但两者之间还有什么不同吗?我正在使用Python 2.6,如果这很重要的话.
我不知道我在这里是否有一个好的设计,但我有一个派生自unittest.TestCase的类和我设置的方式,我的代码会test_*在调用unittest之前动态地将一堆方法注入到类中贯穿它.我用setattr它.这一直运行良好,但现在我有一种情况,我想删除我之前注入的方法并注入一组新的方法.如何删除名称与模式匹配的类中的所有方法test_*?
有很多很好的getattr()函数用于解析嵌套的字典结构,例如:
我想做一个并行的setattr().基本上,给定:
cmd = 'f[0].a'
val = 'whatever'
x = {"a":"stuff"}
Run Code Online (Sandbox Code Playgroud)
我想生成一个我可以分配的功能:
x['f'][0]['a'] = val
Run Code Online (Sandbox Code Playgroud)
或多或少,这将以与以下相同的方式工作:
setattr(x,'f[0].a',val)
Run Code Online (Sandbox Code Playgroud)
产量:
>>> x
{"a":"stuff","f":[{"a":"whatever"}]}
Run Code Online (Sandbox Code Playgroud)
我现在叫它setByDot():
setByDot(x,'f[0].a',val)
Run Code Online (Sandbox Code Playgroud)
这样做的一个问题是,如果中间的密钥不存在,则需要检查并生成中间密钥(如果不存在) - 即,对于上述情况:
>>> x = {"a":"stuff"}
>>> x['f'][0]['a'] = val
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
KeyError: 'f'
Run Code Online (Sandbox Code Playgroud)
所以,你首先必须做:
>>> x['f']=[{}]
>>> x
{'a': 'stuff', 'f': [{}]}
>>> x['f'][0]['a']=val
>>> x
{'a': 'stuff', 'f': [{'a': 'whatever'}]}
Run Code Online (Sandbox Code Playgroud)
另一个是当下一个项目是一个字符串时,键入当下一个项目是一个字符串时,键入不同,即:
>>> x = {"a":"stuff"}
>>> x['f']=['']
>>> x['f'][0]['a']=val
Traceback …Run Code Online (Sandbox Code Playgroud) 尝试使用Python中的getattr和setattr函数访问/分配列表中的项目.不幸的是,似乎无法将列表索引中的位置与列表名称一起传递.
以下是我尝试的一些示例代码:
class Lists (object):
def __init__(self):
self.thelist = [0,0,0]
Ls = Lists()
# trying this only gives 't' as the second argument. Python error results.
# Interesting that you can slice a string to in the getattr/setattr functions
# Here one could access 'thelist' with with [0:7]
print getattr(Ls, 'thelist'[0])
# tried these two as well to no avail.
# No error message ensues but the list isn't altered.
# Instead a new variable is created Ls.'' - printed …Run Code Online (Sandbox Code Playgroud) setattr和getattr那种钻进了我的编程风格(主要是科学的东西,我对蟒蛇知识的自我告知).
考虑到exec并eval继承了潜在的危险,因为在某些情况下它们可能会导致安全问题,我想知道是否setattr认为相同的论点是有效的.(关于getattr我发现这个问题包含一些信息 - 虽然论证不是很有说服力.)
据我所知,setattr可以毫不费力地使用,但说实话,我不相信我的python知识足以确定,如果我错了,我想尝试摆脱使用的习惯setattr.
任何输入都非常感谢!
假设我有一个定义的类__slots__:
class Foo(object):
__slots__ = ['x']
def __init__(self, x=1):
self.x = x
# will the following work?
def __setattr__(self, key, value):
if key == 'x':
object.__setattr__(self, name, -value) # Haha - let's set to minus x
Run Code Online (Sandbox Code Playgroud)
我可以定义__setattr__()吗?
既然Foo没有__dict__,它会更新什么?
是否可以__getitem__使用setattr()?动态地将特殊方法分配给类实例?例如,如果我有这个:
class Example (object):
pass
Run Code Online (Sandbox Code Playgroud)
然后尝试这个:
>>> example = Example()
>>> setattr(example, '__getitem__', lambda x: 1)
Run Code Online (Sandbox Code Playgroud)
我明白了:
>>> example['something']
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: 'Example' object has no attribute '__getitem__'
Run Code Online (Sandbox Code Playgroud)
但当然这很好用:
>>> example.__getitem__('something')
1
Run Code Online (Sandbox Code Playgroud)
这里显然有一些事情,我不明白Python如何为这类事情进行方法查找.是否必须在类上设置这些方法,而不是在实例上设置?
更新:
所以,我应该说清楚,我知道我可以在Example课堂上看到这一点...我希望有一种方法可以在每个实例中设置它们,但我到目前为止看到的共识是你不能这样做.
这个问题可能在某个地方有答案,但我找不到。
我用来setattr向类添加一长串描述符,并且我发现__set_name__当我使用setattr.
这对我来说不是一个大问题,因为我可以通过设置描述符的名称来代替__init__,我只是想了解为什么__set_name__不被调用,以及是否是因为我做错了什么。
class MyDescriptor:
def __set_name__(self, owner, name):
self._owner = owner
self._name = name
def __get__(self, instance, owner):
return self._name
class MyClass:
a = MyDescriptor()
setattr(MyClass, 'b', MyDescriptor()) # dynamically adding descriptor, __set_name__ is not called!
mc = MyClass()
print(mc.a) # prints 'a'
print(mc.b) # raises AttributeError: 'MyDescriptor' object has no attribute '_name'
Run Code Online (Sandbox Code Playgroud)