LINUX.ORG.RU

История изменений

Исправление Virtuos86, (текущая версия) :

class AvoidBoilerplateMeta(type):
    def __new__(cls, name, bases, attrs):
        for (attr, obj) in tuple(attrs.items()):
            if not attr.startswith("_") and isinstance(obj, property):
                def fget(self, a=attr):
                    return getattr(self, "_" + a)
                def fset(self, value, a=attr):
                    setattr(self, "_" + a, value)
                def fdel(self, a=attr):
                    delattr(self, "_" + a)
                attrs[attr] = property(fget, fset, fdel)
        return super(AvoidBoilerplateMeta, cls).__new__(cls, name, bases, attrs)

class Obj(object):
    __metaclass__ = AvoidBoilerplateMeta
    results = property()
    status = property()

    def __init__(self):
        self._results = {"default_result": None}
        self._status = "default_status"

if __name__ == '__main__':
    obj = Obj()
    print obj.results
    print obj.status
    obj.results = {"some_result": 1}
    obj.status = "some status"
    print obj.results
    print obj.status
    del obj.results
    del obj.status
    print obj.results # FAIL: AttributeError: 'Obj' object has no attribute '_results'
    print obj.status # FAIL: AttributeError: 'Obj' object has no attribute '_status'

Не уверен, что реализация наилучшая, но работает :-)

Сообщение об ошибке («AttributeError: …») можно сделать понятнее, но в рамках PoC реализации и так сгодится.

Исправление Virtuos86, :

class AvoidBoilerplateMeta(type):
    def __new__(cls, name, bases, attrs):
        for (attr, obj) in tuple(attrs.items()):
            if not attr.startswith("_") and isinstance(obj, property):
                def fget(self, a=attr):
                    return getattr(self, "_" + a)
                def fset(self, value, a=attr):
                    setattr(self, "_" + a, value)
                def fdel(self, a=attr):
                    delattr(self, "_" + a)
                attrs[attr] = property(fget, fset, fdel)
        return super(AvoidBoilerplateMeta, cls).__new__(cls, name, bases, attrs)

class Obj(object):
    __metaclass__ = AvoidBoilerplateMeta
    results = property()
    status = property()

    def __init__(self):
        self._results = {"default_result": None}
        self._status = "default_status"

if __name__ == '__main__':
    obj = Obj()
    print obj.results
    print obj.status
    obj.results = {"some_result": 1}
    obj.status = "some status"
    print obj.results
    print obj.status
    del obj.results
    del obj.status
    print obj.results # FAIL: AttributeError: 'Obj' object has no attribute '_results'
    print obj.status # FAIL: AttributeError: 'Obj' object has no attribute '_status'

Не уверен, что реализация наилучшая, но работает :-)

Можно сообщение об ошибке («AttributeError: …») можно сделать понятнее, но в рамках PoC реализации и так сгодится.

Исправление Virtuos86, :

class AvoidBoilerplateMeta(type):
    def __new__(cls, name, bases, attrs):
        for (attr, obj) in tuple(attrs.items()):
            if not attr.startswith("_") and isinstance(obj, property):
                def fget(self, a=attr):
                    return getattr(self, "_" + a)
                def fset(self, value, a=attr):
                    setattr(self, "_" + a, value)
                def fdel(self, a=attr):
                    delattr(self, "_" + a)
                attrs[attr] = property(fget, fset, fdel)
        return super(AvoidBoilerplateMeta, cls).__new__(cls, name, bases, attrs)

class Obj(object):
    __metaclass__ = AvoidBoilerplateMeta
    results = property()
    status = property()

    def __init__(self):
        self._results = {"default_result": None}
        self._status = "default_status"

if __name__ == '__main__':
    obj = Obj()
    print obj.results
    print obj.status
    obj.results = {"some_result": 1}
    obj.status = "some status"
    print obj.results
    print obj.status
    del obj.results
    del obj.status
    print obj.results # FAIL: AttributeError: 'Obj' object has no attribute '_results'
    print obj.status # FAIL: AttributeError: 'Obj' object has no attribute '_status'

Не уверен, что реализация наилучшая, но работает :-)

Исходная версия Virtuos86, :

class AvoidBoilerplateMeta(type):
    def __new__(cls, name, bases, attrs):
        for (attr, obj) in tuple(attrs.items()):
            if not attr.startswith("_") and isinstance(obj, property):
                def fget(self, a=attr):
                    return getattr(self, "_" + a)
                def fset(self, value, a=attr):
                    setattr(self, "_" + a, value)
                def fdel(self, a=attr):
                    delattr(self, "_" + a)
                attrs[attr] = property(fget, fset, fdel)
        return super(AvoidBoilerplateMeta, cls).__new__(cls, name, bases, attrs)

class Obj(object):
    __metaclass__ = AvoidBoilerplateMeta
    results = property()
    status = property()

    def __init__(self):
        self._results = {"default_result": None}
        self._status = "default_status"

if __name__ == '__main__':
    obj = Obj()
    print obj.results
    print obj.status
    obj.results = {"some_result": 1}
    obj.status = "some status"
    print obj.results
    print obj.status
    del obj.results
    del obj.status
    print obj.results # FAIL: AttributeError: 'Obj' object has no attribute '_results'
    print obj.status # FAIL: AttributeError: 'Obj' object has no attribute '_

Не уверен, что реализация наилучшая, но работает :-)