2011-05-19 90 views
6

诠释我有一个枚举国籍:转换枚举在Python

class Nationality: 
     Poland='PL' 
     Germany='DE' 
     France='FR' 

我如何转换一些这方面的枚举在这种或类似的方式来诠释:

position_of_enum = int(Nationality.Poland) # here I want to get 0 

我知道我能做到它如果我有代码:

counter=0 
for member in dir(Nationality): 
    if getattr(Nationality, member) == code: 
     lookFor = member 
     counter += 1 
return counter 

但我没有,这种方式看起来太大python。我确信有更简单的事情。

+0

一个类不是枚举。因此,你无法比较。 – 2011-05-19 15:01:38

回答

8

有更好的(和更“pythonic”)做你想做的方式。

要么使用一个元组(或列表,如果需要修改),其中订单将被保留:

code_lookup = ('PL', 'DE', 'FR') 
return lookup.index('PL') 

或者使用词典的线沿线的:

code_lookup = {'PL':0, 'FR':2, 'DE':3} 
return code_lookup['PL'] 

的在我看来,后者更可取,因为它更具可读性和明确性。

一个namedtuple也可能是有用的,在特定情况下,虽然它可能是矫枉过正:

import collections 
Nationalities = collections.namedtuple('Nationalities', 
             ['Poland', 'France', 'Germany']) 
nat = Nationalities('PL', 'FR', 'DE') 
print nat.Poland 
print nat.index(nat.Germany) 
+0

你想念国籍的名字。我必须拥有它们 – user278618 2011-05-19 15:09:08

+0

@ user278618 - 为了简洁起见,我将它们排除在外。这个想法是,你会在你的'国籍'类的某个地方使用某种查询表。您可以轻松替换您的类属性,而不是字符串。 – 2011-05-19 15:22:09

5

你不行。 Python不存储类元素的顺序,并且dir()将以任何顺序返回它们。

从您的评论,你真的确实需要从字符串到整数的映射看,你其实应该做的正是:

code_lookup = { 
    'PL': ("Poland", 0), 
    'DE': ("Germany", 1), 
    'FR': ("France", 2), 
    ... 
} 
+0

我使用这个枚举来设置选择的值,它是在几个不同的CSS和语言的网站,并且只有值属性是在每个站点相同。从这个选择我必须选择国籍,选项的值是0,1,2。我在c#中使用这个投射,所以这是从我接受这个想法。 – user278618 2011-05-19 15:07:10

3

你为什么不只是定义值作为数字而不是字符串:

class Nationality: 
    POLAND = 0 
    GERMANY = 1 
    FRANCE = 2 

如果您需要访问的两个字母的名字,你可以简单地提供它们映射表。 (或另一种方式映射的字典等)

3

我所看到的是这样的:

PL, FR, DE = range(3) 

的一类包裹它,中提琴 ,你有一个枚举的命名空间。

8

无论使用的enum34 backportaenum 您可以创建一个专门的Enum

# using enum34 
from enum import Enum 

class Nationality(Enum): 

    PL = 0, 'Poland' 
    DE = 1, 'Germany' 
    FR = 2, 'France' 

    def __new__(cls, value, name): 
     member = object.__new__(cls) 
     member._value_ = value 
     member.fullname = name 
     return member 

    def __int__(self): 
     return self.value 

,并在使用中:

>>> print(Nationality.PL) 
Nationality.PL 
>>> print(int(Nationality.PL)) 
0 
>>> print(Nationality.PL.fullname) 
'Poland' 

上面更容易编写使用aenum

​​

其具有的附加功能:

>>> Nationality('Poland') 
<Nationality.PL: 0> 

披露:我是Python stdlib Enum的作者,enum34 backportAdvanced Enumeration (aenum)库。

+0

工程很棒。非常感谢! – 2017-01-18 22:23:56