首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >泛型惰性属性getter/setter

泛型惰性属性getter/setter
EN

Stack Overflow用户
提问于 2019-03-25 06:35:28
回答 1查看 232关注 0票数 0

这个问题基于this question关于python类的惰性属性。

我真的很喜欢这里给出的解决方案:

这里是一个惰性属性装饰器的示例实现:

import functools

def lazyprop(fn):
    attr_name = '_lazy_' + fn.__name__

    @property
    @functools.wraps(fn)
    def _lazyprop(self):
        if not hasattr(self, attr_name):
            setattr(self, attr_name, fn(self))
        return getattr(self, attr_name)

    return _lazyprop


class Test(object):

    @lazyprop
    def a(self):
        print 'generating "a"'
        return range(5)

交互式会话:

>>> t = Test()
>>> t.__dict__
{}
>>> t.a
generating "a"
[0, 1, 2, 3, 4]
>>> t.__dict__
{'_lazy_a': [0, 1, 2, 3, 4]}
>>> t.a
[0, 1, 2, 3, 4]

此解决方案允许您为任何属性创建@lazyprop。但是,您必须为您希望成为惰性的每个属性编写一个方法。我需要一些对那些我事先不知道其名称(可能有很多)的属性起作用的东西。

这些属性是从hdf5文件中读取的DataFrames。每个文件包含许多不同的表,我不知道这些表的名称。我有一个很棒的函数get_all_table_names(filename),它可以返回文件中所有表的名称。目前,我遍历所有的名字,并一个接一个地读取它们。然而,有几十GB的数据,需要几分钟才能读入。

有没有一种方法,当一个方法调用一个表时,只读那个表?这里给出的示例非常完美,只是我需要提前知道表的名称。

编辑

将数据从HDF5文件加载到Pandas DataFrame的代码如下所示。

df = read_to_pandas(directory_of_files, 'table_name', number_of_files_to_read)
EN

回答 1

Stack Overflow用户

发布于 2019-03-25 08:43:07

下面是一个通用模板,展示了如何使用动态惰性属性动态生成类:

import functools
import types


def lazyprop(added_value):
    """ Slightly generalize lazy attribute property decorator.
        (i.e. a decorator-factory)
    """
    def prop(fn):
        attr_name = '_lazy_' + fn.__name__ + str(added_value)

        @property
        @functools.wraps(fn)
        def _lazyprop(self):
            if not hasattr(self, attr_name):
                setattr(self, attr_name, fn(self, added_value))
            return getattr(self, attr_name)

        return _lazyprop

    return prop


def make_class(class_name, attrs):

    # Generic methods and class __dict__.
    def __init__(self):
        print('creating instance of class', self.__class__.__name__)

    def getter(self, added_value):
        return 41 + added_value

    cls_dict = {
        '__init__': __init__,
        '__repr__': lambda self: 'class name: %s' % class_name,
    }

    # Create and added lazy attributes.
    for i, attr_name in enumerate(attrs):
        cls_dict[attr_name] = lazyprop(i)(getter)

    cls = types.new_class(class_name, (), {}, lambda ns: ns.update(cls_dict))
    cls.__module__ = __name__

    return cls


if __name__ == '__main__':

    Foobar = make_class('Foobar', ('attr1', 'attr2'))

    foobar = Foobar()    # -> creating instance of class Foobar
    print(foobar)        # -> class name: Foobar
    print(foobar.attr1)  # -> 41
    print(foobar.attr2)  # -> 42
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/55329243

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档