Melvin
Melvin

Reputation: 1600

Purpose of __name__ in TypeVar, NewType

In the typing module, both TypeVar and NewType require as a first positional argument, a string to be used as the created object's __name__ attribute. What is the purpose of __name__ here?

Considering that this is a compulsory argument, I would expect it to be something essential. In PEP-484 where type hinting was introduced, the argument is normally set as a string of the variable name assigned to the object:

T = TypeVar('T', int, float, complex)

But, I can't really tell how this end up being used in typing.py in CPython. Replacing the string with indeed any other string does not appear to break anything in my tests.

Upvotes: 11

Views: 2697

Answers (1)

Arne
Arne

Reputation: 20157

The __name__ attribute is the associated typename that the IDE, for example, will use in its type hints. Given the following toy code:

T = TypeVar('not_T', int, float)
def test_func(arg: T): pass

Calling the function with something incorrect like test_func('not_a_number') would result in a type hint like this:

Expected type 'not_t', got 'str' instead

As far as the python interpreter is concerned, no restrictions are set on conformity between type.__name__ and the name tag you use to handle it, but other third-party tools such as mypy might not accept differing variable name and __name__, which is also a requirement in the intitial typing PEP-484:

The argument to TypeVar() must be a string equal to the variable name to which it is assigned. Type variables must not be redefined.


For an additional use case, you can also check the types in the __annotations__ member of any object where it is used to type hint, e.g.

print(test_func.__annotations__)
>> {'arg': ~not_T}

And use that to implement further type checking or handling in your code - in which case your TypeVar.__name__s better be meaningful :)

Upvotes: 12

Related Questions