首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何测试Python Enum中是否存在int值而不使用try/catch?

如何测试Python Enum中是否存在int值而不使用try/catch?
EN

Stack Overflow用户
提问于 2017-04-26 12:45:10
回答 14查看 111.3K关注 0票数 142

使用Python类,是否有一种方法可以测试Enum是否包含特定的int值而不使用try/catch?

有以下课程:

代码语言:javascript
复制
from enum import Enum

class Fruit(Enum):
    Apple = 4
    Orange = 5
    Pear = 6

如何测试值6(返回true)或值7(返回false)?

EN

回答 14

Stack Overflow用户

回答已采纳

发布于 2017-04-26 12:49:49

价值测试

变式1

请注意,Enum有一个名为_value2member_map_的成员(它是无文档的,可能在以后的python版本中被更改/删除):

代码语言:javascript
复制
print(Fruit._value2member_map_)
# {4: <Fruit.Apple: 4>, 5: <Fruit.Orange: 5>, 6: <Fruit.Pear: 6>}

您可以根据此映射测试Enum中是否有一个值:

代码语言:javascript
复制
5 in Fruit._value2member_map_  # True
7 in Fruit._value2member_map_  # False

变式2

如果您不想依赖此特性,这是另一种选择:

代码语言:javascript
复制
values = [item.value for item in Fruit]  # [4, 5, 6]

或者(可能更好):使用setin运算符将更有效:

代码语言:javascript
复制
values = set(item.value for item in Fruit)  # {4, 5, 6}

然后用

代码语言:javascript
复制
5 in values  # True
7 in values  # False

has_value添加到类中

然后,您可以将其作为方法添加到类中:

代码语言:javascript
复制
class Fruit(Enum):
    Apple = 4
    Orange = 5
    Pear = 6

    @classmethod
    def has_value(cls, value):
        return value in cls._value2member_map_ 

print(Fruit.has_value(5))  # True
print(Fruit.has_value(7))  # False

钥匙测试

如果您想测试名称(而不是值),我将使用_member_names_

代码语言:javascript
复制
'Apple' in Fruit._member_names_  # True
'Mango' in Fruit._member_names_  # False
票数 195
EN

Stack Overflow用户

发布于 2020-07-11 20:57:01

有一种方法可以让所有枚举都能够检查某一项是否存在:

代码语言:javascript
复制
import enum 

class MyEnumMeta(enum.EnumMeta): 
    def __contains__(cls, item): 
        return item in [v.value for v in cls.__members__.values()] 

class MyEnum(enum.Enum, metaclass=MyEnumMeta): 
   FOO = "foo" 
   BAR = "bar"

现在您可以做一个简单的检查:

代码语言:javascript
复制
>>> "foo" in MyEnum
True

如果枚举的所有值都是相同的类型,甚至可以简化--例如字符串:

代码语言:javascript
复制
import enum 
 
class MyEnumMeta(enum.EnumMeta):  
    def __contains__(cls, item): 
        return item in cls.__members__.values()

class MyEnum(str, enum.Enum, metaclass=MyEnumMeta): 
    FOO = "foo" 
    BAR = "bar"

编辑:是另一个版本,技术上是最正确的版本:

代码语言:javascript
复制
import enum 

class MyEnumMeta(enum.EnumMeta): 
    def __contains__(cls, item): 
        try:
            cls(item)
        except ValueError:
            return False
        else:
            return True

class MyEnum(enum.Enum, metaclass=MyEnumMeta): 
   FOO = "foo" 
   BAR = "bar"
票数 38
EN

Stack Overflow用户

发布于 2017-04-26 12:47:20

你可以用Enum.__members__ - https://docs.python.org/3/library/enum.html#iteration

代码语言:javascript
复制
In [12]: 'Apple' in Fruit.__members__
Out[12]: True

In [13]: 'Grape' in Fruit.__members__
Out[13]: False
票数 26
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/43634618

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档