簡體   English   中英

如何鍵入提示 getter 只允許 dict 的鍵?

[英]How to type-hint a getter to only allow keys of dict?

我想知道如何使這個 getter 更類型安全:

VALUES = {
   '1': 'One',
   '2': 'Two',
   '3': 'Three'
}


def get(key : str) -> str:
    return VALUES[key]

我希望擁有一個keyof VALUEStype(VALUES[key])類型,而不是str類型。

get('4')應該拋出一個無效類型警告,因為這個鍵不存在。 不確定這是否可以用 Python 實現,因為我確實生活在 TypeScript 仙境中...... :-)

TypeScript 應該是這樣的:

get<K extends keyof VALUES>(key : K): typeof K
{
    return VALUES[key];
}

一般情況下您不能這樣做 但是,在這種特殊情況下,您可以使用typing.Literal完成您想要的typing.Literal

import typing
def get(key: typing.Literal['1','2','3']) -> str:
    return VALUES[key]

正如評論中所建議的, enum模塊在這里提供了一個很好的解決方案。 通過將strenum.Enum混合,我們可以創建一個與str完全向后兼容的Enum (即,可以在需要str類型的任何地方使用。

from enum import Enum

# The mixin type has to come first if you're combining
# enum.Enum with other types 
class Values(str, Enum):
    N1 = 'One'
    N2 = 'Two'
    N3 = 'Three'

如果我們將此定義輸入到交互式控制台中,我們將看到該類具有以下行為:

>>> Values['N1']
<Values.N1: 'One'>
>>> Values('One')
<Values.N1: 'One'>
>>> Values.N1
<Values.N1: 'One'>
>>> Values('One') is Values.N1 is Values['N1']
True
>>> Values.N1.name
'N1'
>>> Values.N1.value
'One'
>>> Values.N1 == 'One'
True
>>> Values.N1 is 'One'
False
>>> Values.N1.startswith('On')
True
>>> type(Values.N1)
<enum 'Values'>
>>> for key in Values:
...     print(key)
...
Values.N1
Values.N2
Values.N3
>>> list(Values)
[Values.N1, Values.N2, Values.N3]

如您所見,我們定義了一個新類型:

  • 提供對成員的動態字典式訪問,以及更多類型安全的訪問形式。
  • str完全向后兼容——它可以自由地與str對象進行比較,並且可以對其成員使用str方法。
  • 可以在類型提示中用作typing.Literal的替代typing.Literal 如果我有這樣的功能:
def do_something(some_string):
    if some_string not in ('One', 'Two', 'Three'):
        raise Exception('NO.')

然后我可以像這樣注釋它:

from typing import Literal

def do_something(some_string: Literal['One', 'Two', 'Three']) -> None:
   ...

或者像這樣(在這種情況下,您必須傳入Values枚舉的成員而不是普通字符串,否則類型檢查器將引發錯誤):

# Values enum as defined above 
def do_something(some_string: Values) -> None:
   ...

這里有一個更詳細的指導蟒的復雜性Enum Ş這里

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM