2017-09-13 11 views
2

は、この例を考えます。それからintを取得するにはどうすればよいですか? __args__でも__parameters__も、Python 3.5.2では動作しません。より具体的に開梱オプションの型注釈


、私は、関数のシグネチャを検査し、引数に特定の事柄を行い、一般的なデコレータを書くことをしようとしています。そのためには、その後、Tで動作するように、注釈などOptional[T]からクラスを取得する必要があります:私は単に実装に相談することを好むこれらのケースでは

annot = typing.Optional[T] 
cls = # MAGIC?! 
assert cls is T 
+1

あなたは 'annot .__ args __ [0]'(少なくとも3.6.1では)を探しているようです。どのようなPythonバージョンを使用していますか? 'typing'はまだ[暫定](https://www.python.org/dev/peps/pep-0411/)なので、まだ変更が行われている可能性があります。 –

+0

今は3.5で作業する必要があります。 – deceze

+0

あなたは '3.5.2'を使用しています。私は推測していますか? '3.5.1'では' __args__'の名前は '__parameters__'だと思うので、' typing'モジュールの内部APIはかなり揮発性です。) –

答えて

2

3.5.2では、Unionのパラメータを取得するには、__union_params__を使用する必要があります。

>>> from typing import Union 
>>> d = Union[int, str] 
>>> print(*d.__union_params__) 
<class 'int'> <class 'str'> 

これは、残念ながら、唯一3.5.2まで、それは__args__を使用する3.5.3に変更された適用に思える:

>>> from typing import Union 
>>> t = Union[int, str] 
>>> t.__union_params__ 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
AttributeError: '_Union' object has no attribute '__union_params__' 
>>> print(*t.__args__) 
<class 'int'> <class 'str'> 

をし、それ以降のバージョン(3.63.7)で__args__を推移しています。

これは、タイピングモジュールの仮のステータスによるものです。内部APIの多くの側面がマイクロバージョン間で変化しているので、おそらく多くの不明確な変更に対処する必要があります。

2

を。 3.5.2では、これは__repr__ of Unionです:

def __repr__(self): 
    r = super().__repr__() 
    if self.__union_params__: 
     r += '[%s]' % (', '.join(_type_repr(t) 
           for t in self.__union_params__)) 
    return r 

これは、クラスは__union_params__属性に格納されることを示唆している:

typing.get_type_hints(foo)['bar'].__union_params__[0] is T 

これは、しかし、3.5.3のためthe commit 5fc25a873cfdec27e46f71e62c9b65df5667c1b4__args__に変更されました。