pytoolz / toolz

A functional standard library for Python.
http://toolz.readthedocs.org/
Other
4.71k stars 263 forks source link

TYP: annotate curry #516

Closed twoertwein closed 2 years ago

twoertwein commented 3 years ago

This mirrors the type annotations of functools.partial.

twoertwein commented 3 years ago

I'm currently using / which requires python 3.8+ to avoid parameter name collisions (curry(some_function, func=some_keyword)). Name collisions could also be "avoided" by using a random name for func.

One big difference to functools.partial is that curry can either return another curry object or the return value of the wrapped function. I'm not sure whether typing this function makes sense: __call__ has to return Union[_T, curry[_T]] which does not make it particularly useful.

@eriknw

eriknw commented 3 years ago

Thanks for this! I'm eager to get type annotations in toolz.

I also look forward to only supporting Python 3.8+, and am eager to use the / syntax in function signatures. This will need to wait until the end of the year. Many dependents of toolz follow NEP 29, which suggests which Python versions should be supported.

mrocklin commented 3 years ago

My preference would be for toolz to be more conservative than NEP 29. It tries to be more core in the stack than most projects. My hope is that we can still get a lot of typing done without /

eriknw commented 3 years ago

Agreed, and historically it has cost us little to support older versions of Python.

twoertwein commented 3 years ago

I think I found an ugly way to avoid /. Let's see what the CI says about older python versions.

With python 3.9.5

from toolz.functoolz import curry

def fun(test: str) -> int:
    return 1

reveal_type(curry(fun))

mypy: note: Revealed type is "toolz.functoolz.curry[builtins.int*]" pyright: info: Type of "curry(fun)" is "curry[int]"

twoertwein commented 3 years ago

The current version should work on python>=3.5. The second overload is just used to silence mypy.

Is it possible to run the CI again?