2018年3月10日 星期六

[Python 範例代碼] DECORATORS FOR ADDING ALIASES TO METHODS IN A CLASS

Source From Here 
The following recipe can be used as a means to adding aliases to methods in a class
- utils.py 
  1. class alias(object):  
  2.     """  
  3.     Alias class that can be used as a decorator for making methods callable  
  4.     through other names (or "aliases").  
  5.     Note: This decorator must be used inside an @aliased -decorated class.  
  6.     For example, if you want to make the method shout() be also callable as  
  7.     yell() and scream(), you can use alias like this:  
  8.   
  9.         @alias('yell''scream')  
  10.         def shout(message):  
  11.             # ....  
  12.     """  
  13.   
  14.     def __init__(self, *aliases):  
  15.         """Constructor."""  
  16.         self.aliases = set(aliases)  
  17.   
  18.     def __call__(self, f):  
  19.         """  
  20.         Method call wrapper. As this decorator has arguments, this method will  
  21.         only be called once as a part of the decoration process, receiving only  
  22.         one argument: the decorated function ('f'). As a result of this kind of  
  23.         decorator, this method must return the callable that will wrap the  
  24.         decorated function.  
  25.         """  
  26.         f._aliases = self.aliases  
  27.         return f  
  28.   
  29.   
  30. def aliased(aliased_class):  
  31.     """  
  32.     Decorator function that *must* be used in combination with @alias  
  33.     decorator. This class will make the magic happen!  
  34.     @aliased classes will have their aliased method (via @alias) actually  
  35.     aliased.  
  36.     This method simply iterates over the member attributes of 'aliased_class'  
  37.     seeking for those which have an '_aliases' attribute and then defines new  
  38.     members in the class using those aliases as mere pointer functions to the  
  39.     original ones.  
  40.   
  41.     Usage:  
  42.         @aliased  
  43.         class MyClass(object):  
  44.             @alias('coolMethod''myKinkyMethod')  
  45.             def boring_method():  
  46.                 # ...  
  47.   
  48.         i = MyClass()  
  49.         i.coolMethod() # equivalent to i.myKinkyMethod() and i.boring_method()  
  50.     """  
  51.     original_methods = aliased_class.__dict__.copy()  
  52.     for name, method in original_methods.iteritems():  
  53.         if hasattr(method, '_aliases'):  
  54.             # Add the aliases for 'method', but don't override any  
  55.             # previously-defined attribute of 'aliased_class'  
  56.             for alias in method._aliases - set(original_methods):  
  57.                 setattr(aliased_class, alias, method)  
  58.     return aliased_class  
Then you can use it this way: 
- test.py 
  1. from utils import *  
  2.   
  3. @aliased  
  4. class People:  
  5.     def __init__(self, name, age):  
  6.         self.name = name  
  7.         self.age = age  
  8.   
  9.     @alias('n''showname')  
  10.     def getname(self):  
  11.         print('My name is {}'.format(self.name))  
  12.   
  13.     @alias('a''showage')  
  14.     def getage(self):  
  15.         print('My age is {}'.format(self.age))  
  16.   
  17. pe = People('John'37)  
  18. pe.getname()  
  19. pe.getage()  
  20. pe.n()  
  21. pe.a()  
The execution result: 
# python test.py
My name is John
My age is 37
My name is John
My age is 37

Supplement 
Python 文章收集 - A guide to Python's function decorators

沒有留言:

張貼留言

[ Python 文章收集 ] SQLAlchemy quick start with PostgreSQL

Source From   Here   Preface   This is a quick tutorial for getting started with   SQLAlchemy Core API .   Prerequisites   In this quick st...