我正在用Python编写脚本,但有一个问题:
class LightDMUser(QObject):
def __init__(self, user):
super(LightDMUser, self).__init__()
self.user = user
@pyqtProperty(QVariant)
def background(self): return self.user.get_background()
@pyqtProperty(QVariant)
def display_name(self): return self.user.get_display_name()
@pyqtProperty(QVariant)
def has_messages(self): return self.user.get_has_messages()
@pyqtProperty(QVariant)
def home_directory(self): return self.user.get_home_directory()
@pyqtProperty(QVariant)
def image(self): return self.user.get_image()
@pyqtProperty(QVariant)
def language(self): return self.user.get_language()
@pyqtProperty(QVariant)
def layout(self): return self.user.get_layout()
@pyqtProperty(QVariant)
def layouts(self): return self.user.get_layouts()
@pyqtProperty(QVariant)
def logged_in(self): return self.user.get_logged_in()
@pyqtProperty(QVariant)
def name(self): return self.user.get_name()
@pyqtProperty(QVariant)
def real_name(self): return self.user.get_real_name()
@pyqtProperty(QVariant)
def session(self): return self.user.get_session()
如您所见,此代码非常多余。我试着像这样压缩它:
class LightDMUser(QObject):
attributes = ['background', 'display_name', 'has_messages', 'home_directory', 'image', 'language', 'layout', 'layouts', 'logged_in', 'name', 'real_name', 'session']
def __init__(self, user):
super(LightDMUser, self).__init__()
self.user = user
for attribute in self.attributes:
setattr(self, attribute, pyqtProperty(QVariant, getattr(self.user, 'get_' + attribute)))
但是,PyQt4期望为类本身而不是实例提供类方法。因为没有为该类定义setattr
代码,所以将代码移出该__init__
块也不起作用self
,所以我真的不知道该怎么做。
谁能看到压缩此代码的方法?
有很多方法可以做到:类装饰器,元类和Mixin。
常用助手功能:
def set_pyqtproperties(klass, properties, proxy='user'):
def make_prop(prop):
def property_(self):
return getattr(getattr(self, proxy), 'get_' + prop)
property_.__name__ = prop
return property_
if isinstance(properties, basestring):
properties = properties.split()
for prop in properties:
setattr(klass, prop, pyqtProperty(QVariant, make_prop(prop)))
def set_properties(properties):
def decorator(klass):
set_pyqtproperties(klass, properties)
return klass
return decorator
用法
@set_properties("display background")
class LightDMUser(QObject): pass
如果不支持类装饰器,则可以尝试:
class LightDMUser(QObject):
pass
LightDMUser = set_properties("display background")(LightDMUser)
def set_properties_meta(properties):
def meta(name, bases, attrs):
cls = type(name, bases, attrs)
set_pyqtproperties(cls, properties)
return cls
return meta
用法
class LightDMUser(QObject):
__metaclass__ = set_properties_meta("display background")
注意:如果将属性列表设置为类属性,则可以重用同一元类:
def MetaClass(name, bases, attrs):
cls = type(name, bases, attrs)
set_pyqtproperties(cls, attrs.get('properties', ''))
return cls
class LightDMUser(QObject):
properties = "display background"
__metaclass__ = MetaClass
另外,您可以attrs
直接attrs[name] = value
进行操作:在调用之前type()
代替setattr(cls, name, value)
。
以上假设QObject.__class__ is type
。
def properties_mixin(classname, properties):
#note: create a new class by whatever means necessary
# e.g., even using exec() as namedtuple does
# http://hg.python.org/cpython/file/3.2/Lib/collections.py#l235
# reuse class decorator here
return set_properties(properties)(type(classname, (), {}))
用法
PropertiesMixin = properties_mixin('PropertiesMixin', 'display background')
class LightDMUser(PropertiesMixin, QObject): pass
我还没有尝试过。这里的代码显示了实现该功能可能需要的数量和代码种类。
我有一个这样的事件来源 我需要通过用户过去的网页访问来丰富我的事件流。(我在数据库中拥有信息,我可以将其用作Flink源) 如何确保在开始处理事件流之前,我已经准备好了扩展数据 我不想从流中进行DB调用。
在我的主要活动中,我有initUi函数,它将触发对webviewActivity的意图,在webviewActivity中,有一个FragWebView,其中加载了url。 以下是来自FragWebView的示例代码: 我从我的主要活动中传递打开webview的意图是: 请让我知道如何解决这个问题。 问候
当我试图编写一个与listview项交互的代码时,我得到了一个OmbyuousViewMatcherException异常。场景如下。 我有一个包含两个视图的listview 文本视图 按钮查看 我在列表中有将近250行。所有按钮都有文本“预订”或“取消”。他们在一个洗牌的顺序。我想直接点击列表中的第一个“预订它”按钮。我已经尝试了很多方案,但仍然无法找到解决方案。拜托谁帮帮我。 下面是我现在的代
我试着用“浓缩咖啡”写简单的测试 但我有个错误: 我正在尝试不同的框架进行测试,对我来说是最好的,但如果有人能帮助修复这个错误,我将非常感激
本文向大家介绍Android 设置意式浓缩咖啡,包括了Android 设置意式浓缩咖啡的使用技巧和注意事项,需要的朋友参考一下 示例 在build.gradle您的Android应用模块的文件中,添加下一个依赖项: 在文件中AndroidJUnitRunner为testInstrumentationRunner参数指定build.gradle。 此外,添加此依赖项以提供意图模拟支持 并将其添加为w
在Espresso中,应用程序启动,测试以以下代码开始:onView(withId(r.id.choosebooktitle)).perform(click()); 这会崩溃,因为显示器仍然显示启动屏幕,而chooseBookTitle只有在之后才可见。如何防止谷歌-浓缩咖啡会在它出现之前点击键? (我不想插入等待循环,而是保持事件驱动。在更糟糕的情况下,我回到Robotium)