Python class member lazy initialization

前端 未结 5 2083
Happy的楠姐
Happy的楠姐 2021-02-01 18:37

I would like to know what is the python way of initializing a class member but only when accessing it, if accessed. I tried the code below and it is working but is there somethi

5条回答
  •  孤独总比滥情好
    2021-02-01 19:03

    Another approach to make the code cleaner is to write a wrapper function that does the desired logic:

    def memoize(f):
        def wrapped(*args, **kwargs):
            if hasattr(wrapped, '_cached_val'):
                return wrapped._cached_val
            result = f(*args, **kwargs)
            wrapped._cached_val = result
            return result
        return wrapped
    

    You can use it as follows:

    @memoize
    def expensive_function():
        print "Computing expensive function..."
        import time
        time.sleep(1)
        return 400
    
    print expensive_function()
    print expensive_function()
    print expensive_function()
    

    Which outputs:

    Computing expensive function...
    400
    400
    400
    

    Now your classmethod would look as follows, for example:

    class MyClass(object):
            @classmethod
            @memoize
            def retrieve_data(cls):
                print "Computing data"
                import time
                time.sleep(1) #costly DB call
                my_data = 40
                return my_data
    
    print MyClass.retrieve_data()
    print MyClass.retrieve_data()
    print MyClass.retrieve_data()
    

    Output:

    Computing data
    40
    40
    40
    

    Note that this will cache just one value for any set of arguments to the function, so if you want to compute different values depending on input values, you'll have to make memoize a bit more complicated.

提交回复
热议问题