从包含字典作为值的列表中检索数据 (python)

To retrieve data from list where it contains dictionary as its values (python)

我是 python 的新手,试图理解这些概念。我正在尝试遍历一个列表,在列表内部,我保留了已初始化的字典数据集。我已经定义了遍历和检索数据的函数。

最初,第一个键和值将分配给 activeConfiguration 列表 i,e activeConfiguration = ['Mammals','dogs'],并且此 activeConfiguration 与实体数据一起作为参数传递给 getNextConfig(data, activeConfiguration) 函数。

我的目标是,在我进行函数调用 getNextConfig(data, activeConfiguration) 的某些特定步骤后,它应该从特定键的列表中检索下一个值。我在下面指定的预期结果。

我的代码有错误,请帮助我修复并获得预期的结果。 提前感谢您的帮助。

#实体数据初始化

vertebrateAnimalsDict = [
   
    {
        "Reptiles": "Snakes, lizards, crocodiles, alligators, turtles"
    },
    
    {
        "Mammals": "dogs, cats, horses, duckbill platypuses, kangaroos, dolphins, whales"
    },

    {
        "Minibeasts": "Insects, spiders, crustaceans"
    }
]

我的函数调用:

activeConfiguration = ['Mammals','dogs']

activeConfiguration = getNextConfig(vertebrateAnimalsDict, activeConfiguration)
print(activeConfiguration)

#some tasks in between
 ...
activeConfiguration = getNextConfig(vertebrateAnimalsDict, activeConfiguration)
print(activeConfiguration)

#some other tasks inbetween
...
activeConfiguration = getNextConfig(vertebrateAnimalsDict, activeConfiguration)
print(activeConfiguration)            

我的代码:

#!/usr/bin/env python
   
def getNextConfig(data, activeConfiguration):
    key_count=len([ele for ele in data if isinstance(ele,dict)])
    val_index=-1   
    for dic in data:   
        for k,v in dic.items(): 
            if k==activeConfiguration[0]:                
                key_index=next((i for i,d in enumerate(data) if k in d), None)
                v=data[key_index][k]
                v = v.split(',')                
                val_index=v.index(activeConfiguration[1])
                if val_index != (len(v)-1):                    
                    return [k,v[val_index+1]]
                elif key_index==(key_count-1) and val_index == (len(v)-1):
                    return []
                else:
                    val_index=0
                    key_index=key_index+1
                    break
                
            if val_index==0:
                v=data[key_index][k]
                v = v.split(',')
                return [k,v[val_index]] 
            else:
                continue 

                       

我的预期输出结果:-

Reptiles : Snakes
Reptiles : lizards
Reptiles : crocodiles
Reptiles : alligators
Reptiles : turtles
Mammals  : dogs
Mammals  : cats
and so on ...

执行以下操作会很简单:

从字典列表中创建一个字典:

dict1 = {k: v.split(", ") for x in vertebrateAnimalsDict for k, v in x.items()}

编辑:

将其转换为一个系列并分解(因此值列表中的每一项都在不同的行上):

pairs = pd.Series(dict1).explode()

这个小函数:

def getNextConfig(pair):
    # get list of bools for whether item matches, and "shift"
    x = pairs[[False] + list(pairs == pair[1])[:-1]]
    # print the pair, for example
    print([x.index.item(), x.item()])
    # return the pair
    return [x.index.item(), x.item()]

然后运行代码从头开始:

pair = ["Reptiles", "Snakes"]
pair = getNextConfig(pair) # repeat this line to the end (and error on the very last, where it cannot continue)

以及旧答案的循环,以防万一您决定循环遍历每个组合或希望在将来这样做:

for k, v in dict1.items():
    for idx in range(len(v)):
        print([k, v[idx]])
        
        # the other code here...

编辑 2:

在不使用 Pandas 的情况下,您可以改为“翻转”字典:

pairs = {}

for k, v in dict1.items():
    for idx in range(len(v)):
        pairs.update({v[idx]: k})

由于爬行动物、哺乳动物和小型动物列表中的所有项目都是唯一的,您可以将值更改为键,将这三个类别更改为值。

然后在调用函数时你可以在返回对时反转这些(我写了一个列表理解来搜索键列表,“动物”,而不是在 Pandas 系列中搜索值) :

def getNextConfig(pair):
    # get list of bools for whether item matches, and "shift"
    p = [i+1 for i, y in enumerate(pairs.keys()) if y==pair[1]][0]
    if len(pairs.keys()) <= p:
        # print statement if out of items
        print("Previous pair was last pair")
        # return same pair (i.e. the last pair)
        return pair
    # animal
    x = list(pairs.keys())[p]
    # print the pair
    print([pairs[x], x])
    # return the pair
    return [pairs[x], x]

请注意,我为最后一对添加了 if 语句,以便您可以编写特定的消息。

如果我没有正确理解你的问题,你可以使用生成器来迭代值:

def getNextConfig(data):
    for dic in data:
        for key, value in dic.items():
            values = value.split(', ')
            for v in values:
                yield key, v

然后您可以像这样遍历它:

configs = getNextConfig(vertebrateAnimalsDict)
for k, v in configs:
    print(f'{k} : {v}')

输出(对于您的示例数据):

Reptiles : Snakes
Reptiles : lizards
Reptiles : crocodiles
Reptiles : alligators
Reptiles : turtles
Mammals : dogs
Mammals : cats
Mammals : horses
Mammals : duckbill platypuses
Mammals : kangaroos
Mammals : dolphins
Mammals : whales
Minibeasts : Insects
Minibeasts : spiders
Minibeasts : crustaceans

或者为了匹配问题中的代码风格,我们使用 next 从生成器中获取下一个值:

configs = getNextConfig(vertebrateAnimalsDict)
activeConfiguration = next(configs, None)
if activeConfiguration is not None:
    # do something with it

请注意,我们为 next 提供了默认值以避免 StopIteration 错误。