Skip to content

can't pickle lru_cache function with loky #292

Description

@basnijholt

The following fails:

from functools import lru_cache
import adaptive
adaptive.notebook_extension()

@lru_cache
def g(x):
    return x

def f(x):
    return g(x)

learner = adaptive.SequenceLearner(f, range(2))
runner = adaptive.Runner(learner, adaptive.SequenceLearner.done)

runner.live_info()

Related to loky issue: joblib/loky#268

This worked fine with the concurrent.futures.ProcessPoolExecutor.

Activity

  1. basnijholt commented on Sep 2, 2020

    @basnijholt
    MemberAuthor

    This is because of cloudpipe/cloudpickle#178
    and can be reproduced with

    import cloudpickle
    from functools import lru_cache
    
    @lru_cache
    def g(x):
        return x
    
    dump = cloudpickle.dumps(g)
    del g
    g = cloudpickle.loads(dump)
    g(1)
  2. akhmerov commented on Sep 2, 2020

    @akhmerov
    Contributor

    What's the use case for lru_cache'd functions?

  3. basnijholt commented on Sep 2, 2020

    @basnijholt
    MemberAuthor

    This occurs in some simulation software I use.

    For example

    @lru_cache
    def make_kwant_syst():
        ...
        return syst
    
    def f(x):
        syst = make_kwant_syst()
        return conductance(x, syst)
  4. akhmerov commented on Sep 2, 2020

    @akhmerov
    Contributor

    I see. In the meantime you could hack around it by making syst global:

    def make_kwant_syst():
        try:
            return syst
        except NameError:
            global syst = ...
            return syst
  5. basnijholt commented on Sep 2, 2020

    @basnijholt
    MemberAuthor

    Also, it seems like this is blocked until at least the release of Python 3.9: cloudpipe/cloudpickle#309 (comment).

    Other alternatives include using your own memorization decorator:

    def memoize(f):
        memo = {}
        def helper(x):
            if x not in memo:            
                memo[x] = f(x)
            return memo[x]
        return helper

    or using the concurrent.futures.ProcessPoolExecutor.

  6. akhmerov commented on Sep 2, 2020

    @akhmerov
    Contributor

    Should we then close this as an upstream bug? It seems like it will require no action either way.

  7. basnijholt commented on Sep 2, 2020

    @basnijholt
    MemberAuthor

    I think closing it will suggest that it's fixed. I rather leave it open with the "Blocked" label attached.

  8. akhmerov commented on Sep 2, 2020

    @akhmerov
    Contributor

    But it's just not our bug, that is the reason to close it.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions