hgrecco / pint

Operate and manipulate physical quantities in Python
http://pint.readthedocs.org/
Other
2.32k stars 456 forks source link

Pint typing (again?) #1679

Open jldiaz opened 1 year ago

jldiaz commented 1 year ago

According to this comment, https://github.com/hgrecco/pint/pull/1259#issuecomment-848086093 typing integration is done, and working with mypy. This is not my experience. I'm using pint 0.20.1 and mypy 0.991 and any Quantity is inferred as type Any by mypy.

I tried this example:

from pint import UnitRegistry

ureg = UnitRegistry()

float_quantity = ureg.Quantity(150.0, "m**2")
int_quantity = ureg.Quantity(150, "m**2")
list_quantity = ureg.Quantity((1, 2, 3, 4), "m**2")
str_quantity = ureg.Quantity("50*2 m")
sequence = [ureg.Quantity(2, "m"), ureg.Quantity(3, "m")]

reveal_type(float_quantity)
reveal_type(int_quantity)
reveal_type(float_quantity.m)
reveal_type(float_quantity.to("km**2"))
reveal_type(str_quantity)
reveal_type(list_quantity)

And ran it through mypy, but the output was puzzling:

typetest.py:11: note: Revealed type is "Any"
typetest.py:12: note: Revealed type is "Any"
typetest.py:13: note: Revealed type is "Any"
typetest.py:14: note: Revealed type is "Any"
typetest.py:15: note: Revealed type is "Any"
typetest.py:16: note: Revealed type is "Any"
Success: no issues found in 1 source file

Why is this? Something was changed in pint or in mypy? Did I miss something?

Note Also Pylance (Microsoft's python type checker powered by Pyright, used by VSCode) infers the type Any for all these variables. Pylance version is v2022.12.20.

austinorr commented 1 year ago

@jldiaz Hi there, I just had this same issue and dove in to the type checker code. This PR ( #1686 ) fixed this regression for me, can you give it a try and let me know if it would close this issue for you as well? I'd rather not open extra issues here if I can avoid it!

jldiaz commented 1 year ago

@austinorr Thank you for your reply.

Unfortunately PR #1686 does not solve the problem of Quantity being considered of type Any, and in addition it introduces new problems at every line which uses ureg.Quantity() to build a quantity. Mypy output is now:

typetest.py:5: error: "PlainQuantity[Any]" not callable  [operator]
typetest.py:6: error: "PlainQuantity[Any]" not callable  [operator]
typetest.py:7: error: "PlainQuantity[Any]" not callable  [operator]
typetest.py:8: error: "PlainQuantity[Any]" not callable  [operator]
typetest.py:9: error: "PlainQuantity[Any]" not callable  [operator]
typetest.py:11: note: Revealed type is "Any"
typetest.py:12: note: Revealed type is "Any"
typetest.py:13: note: Revealed type is "Any"
typetest.py:14: note: Revealed type is "Any"
typetest.py:15: note: Revealed type is "Any"
typetest.py:16: note: Revealed type is "Any"
Found 5 errors in 1 file (checked 1 source file)
jules-ch commented 1 year ago

I think we need to add back typing of Quantity attribute of the UnitRegistry to Type[PlainQuantity]. The change to facets is making Quantity Class even more dynamic, so it's harder to static typing this part of the code.