如何在m次迭代中使用n代替n来实现if-else

时间:2014-08-22 20:35:17

标签: python

我迭代了一个词典列表:

dictList=[{1:'One'}, {2:'Two'), {1:'One',7:'Seven'}]
result=[eachDict.get(1) for eachDict in dictList if eachDict.get(1)]

检查是否显示字典键1。如果1密钥不在字典中,我希望它返回密钥7(而不是1密钥)。 再次,如果有密钥1返回它。如果没有1密钥,请尝试返回7密钥。怎么做到这一点?

4 个答案:

答案 0 :(得分:3)

老实说,我认为这在循环中更容易。没有理由总是尝试将所有内容混合到列表理解中。有时for循环更容易编写,阅读,理解和扩展。

dictlist = [{1: 'One'}, {2: 'Two'}, {1: 'One', 7: 'Seven'}]

result = []
for d in dictlist:
    if 1 in d:
        result.append(d[1])
    elif 7 in d:
        result.append(d[7])
    # else:
    #     Possibly do something here?

如果效率很重要,有些时间

def my_func():
    result = []
    for d in dictlist:
        if 1 in d:
            result.append(d[1])
        elif 7 in d:
            result.append(d[7])
        else:
            result.append(None)  # To match their implementations

%timeit my_func()  # My answer
# 1000000 loops, best of 3: 646 ns per loop

%timeit [d.get(1) if 1 in d else d.get(7) for d in dictList]  # Hamatti's answer
# 1000000 loops, best of 3: 808 ns per loop

%timeit [d.get(1, d.get(7)) for d in dictList]  # Peter DeGlopper's answer
# 1000000 loops, best of 3: 1.07 us per loop

但请记住,这些时间是在提供的d上完成的。我不知道所有这些如何扩展到更大的词典,或者你正在做什么样的规模。如果它不是非常更大,那么效率根本不重要。

答案 1 :(得分:3)

您可以执行以下操作

>> dictList=[{1:'One'}, {2:'Two'}, {7:'Seven'}]
>> [d.get(1) if 1 in d else d.get(7) for d in dictList]
['One', None, 'Seven']

答案 2 :(得分:3)

Roger Fan的回答很好,但是如果你真的想要简明扼要,可以使用嵌套的get作为替代方案:

result = [d.get(1, d.get(7)) for d in dictList]

这会查找两个值,因为Python总是评估其所有函数调用的参数 - get不会短路。因此,与迭代方法相比,它的效率略低。我认为Hamatti的答案是等效的,每次进行两次键查找(一次检查in,一次选择get,但这些都不会产生性能问题。

满足不为缺少两个键的dicts添加None的要求的一种方法是这种丑陋:

result = [x for x in (d.get(1, d.get(7)) for d in dictList) if x]

它使用内部生成器对象,因此它不会遍历两次。但在那时我肯定会使用for循环。

答案 3 :(得分:1)

对于要查找的几个元素,请坚持使用其他解决方案,但如果您有更多的键,那么 if / elif / else 的长列表不是很好,所以您可以创建返回第一个可用元素的自定义getter:

def firstgetter(*items):
    def getter(dic):
        for item in items:
            if item in dic:
                return dic[item]
    return getter

实施例

dictList=[{1: 'One'}, {2: 'Two'}, {2: 'Two', 7: 'Seven'}]
map(firstgetter(1, 7), dictList)  # ['One', None, 'Seven']