From f68ac6176478d2fe98b46de714fcbc4bf3ebd123 Mon Sep 17 00:00:00 2001 From: Albert Zeyer Date: Tue, 8 Oct 2024 12:32:39 +0200 Subject: [PATCH] hash get_object_state, use dir for native types, fix __slots__ Fix #207 --- sisyphus/hash.py | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/sisyphus/hash.py b/sisyphus/hash.py index dd5893d..5324fd8 100644 --- a/sisyphus/hash.py +++ b/sisyphus/hash.py @@ -52,10 +52,19 @@ def get_object_state(obj): if hasattr(obj, "__sis_state__"): state = obj.__sis_state__() + elif getattr(obj, "__class__", None) and getattr(obj.__class__, "__dictoffset__", 0) > 0: + # This type has some native attribs, which are not in __dict__ (and neither in __slots__). + # `dir()` should be able to list those. + # One example is the native `_functools.partial`. + # https://github.com/rwth-i6/sisyphus/issues/207 + return {k: getattr(obj, k) for k in dir(obj) if not k.startswith("__")} elif hasattr(obj, "__getstate__"): state = obj.__getstate__() - elif hasattr(obj, "__dict__"): + elif hasattr(obj, "__dict__") and not hasattr(obj, "__slots__"): state = obj.__dict__ + elif hasattr(obj, "__dict__") and hasattr(obj, "__slots__"): + state = obj.__dict__.copy() + state.update({k: getattr(obj, k) for k in obj.__slots__ if hasattr(obj, k)}) elif hasattr(obj, "__slots__"): state = {k: getattr(obj, k) for k in obj.__slots__ if hasattr(obj, k)} else: