【问题标题】:How do you use loop to assign dictionary value based upon key您如何使用循环根据键分配字典值
【发布时间】:2018-11-15 14:56:48
【问题描述】:

我正在尝试遍历用于创建字典键并根据几个不同类别分配值的列表

例如:

list = ['cat1', 'cat2', 'cat3', 'number1', 'number2', 'number3']

my_dict = {}

for i in range(len(list)):
     if any("cat" in s for s in list):
          my_dict[list[i]] = 'categorical'
     if any("num" in s for s in list):
          my_dict[list[i]] = 'numerical'  

我正在尝试获取一个会循环并导致结果的字典:

my_dict = {'cat1': 'categorical', 'cat2': 'categorical', 'cat3': 'categorical', 'number1': 'numerical', 'number2': 'numerical', 'number3': 'numerical'}

感谢您的帮助!

【问题讨论】:

  • 不要列出list,它会覆盖内置名称。

标签: python dictionary for-loop


【解决方案1】:

如果您可以假设列表中的值将匹配您的查找之一,您可以这样做:

items = ['cat1', 'cat2', 'cat3', 'number1', 'number2', 'number3']
matches = {'num': 'numerical', 'cat': 'categorical'}
result = {i: [v for k, v in matches.items() if k in i][0] for i in items}
print(result)

如何?

这使用 dict 将所需的搜索字符串映射到匹配的值。然后它使用循环理解来搜索字典中的每个值并返回匹配的值。该值用作dict理解中的值。

结果:

{'cat1': 'categorical', 'cat2': 'categorical', 'cat3': 'categorical',
 'number1': 'numerical', 'number2': 'numerical', 'number3': 'numerical'
}

【讨论】:

    【解决方案2】:

    您的示例非常接近,但存在一些问题。这是一个尽可能少地修改代码的解决方案:

    lst = ['cat1', 'cat2', 'cat3', 'number1', 'number2', 'number3']
    
    my_dict = {}
    
    for value in lst:
         if "cat" in value:
              my_dict[value] = 'categorical'
         if "num" in value:
              my_dict[value] = 'numerical'  
    

    第一个主要问题是你永远不应该覆盖一个内置的。使用 lst 或 list_ 不列出。

    现在让我们看看你的这段代码:

    if any("cat" in s for s in lst):
    

    ...正如您所拥有的,这会检查“cat”是否出现在列表中的任何位置(不仅仅是在您要检查的项目中)。

    既然这是真的,'cat1' 将被分配给分类。但是因为您有另一个 if 语句也对数值计算为 true,所以 此结果将被覆盖,您最终会将所有条目列为数值。

    【讨论】:

    • 为什么是enumerate?
    • 我把它去掉了,原来的代码使用了索引,所以我想到了。很好,谢谢
    【解决方案3】:

    稍微修改一下你的代码;使用startswith 查找匹配项:

    lst = ['cat1', 'cat2', 'cat3', 'number1', 'number2', 'number3']
    
    my_dict = {}
    
    for x in lst:
        if x.startswith('cat'):
            my_dict[x] = 'categorical'
        elif x.startswith('num'):
            my_dict[x] = 'numerical'
    
    print(my_dict)
    
    # {'cat1': 'categorical', 'cat2': 'categorical', 'cat3': 'categorical', 'number1': 'numerical', 'number2': 'numerical', 'number3': 'numerical'}
    

    【讨论】:

      【解决方案4】:

      斯蒂芬·劳赫有一个好主意。这是他使用dict.get 编写的内容的稍微简洁的版本。

      matches = {'num': 'numerical', 'cat': 'categorical'}
      result = {k : matches.get(k[:3], 'unknown') for k in items}
      

      print(result)
      {'cat1': 'categorical',
       'cat2': 'categorical',
       'cat3': 'categorical',
       'number1': 'numerical',
       'number2': 'numerical',
       'number3': 'numerical'}
      

      如果要删除不匹配的值,请稍作修改:

      result = {k : matches[k[:3]] for k in items if k[:3] in matches}
      

      这是我的看法。先排序items,然后找到不连续的索引。

      items.sort()
      
      for i, l in enumerate(items):
          if l.startswith('num'):
              break
      
      result = dict.fromkeys(items[:i], 'categorical')
      result.update(dict.fromkeys(items[i:], 'numerical'))
      

      这仅适用于两类值。

      print(result)
      {'cat1': 'categorical',
       'cat2': 'categorical',
       'cat3': 'categorical',
       'number1': 'numerical',
       'number2': 'numerical',
       'number3': 'numerical'}
      

      【讨论】:

      • @StephenRauch 不,不会,当然不如选项 1 灵活!
      • 我喜欢这里的get()。
      • @StephenRauch 是的,我也喜欢你的回答。非常灵活。
      【解决方案5】:

      最简单的答案:

      l = ['cat1', 'cat2', 'cat3', 'number1', 'number2', 'number3', 'junk']
      d = {k: 'categorical' if 'cat' in k else 'numerical' if 'number' in k else 'unknown' for k in l}
      

      输出:

      {'cat1': 'categorical', 'cat2': 'categorical', 'cat3': 'categorical', 'number1': 'numerical', 'number2': 'numerical', 'number3': 'numerical', 'junk': 'unknown'}
      

      【讨论】:

        【解决方案6】:

        尝试使用字典setdefault函数:

        l = ['cat1', 'cat2', 'cat3', 'number1', 'number2', 'number3']
        my_dict = {}
        for i in l:
            my_dict.setdefault(i,['numerical' if 'number' in i else 'category'][-1])  
        print(my_dict)
        

        输出:

        {'cat1': 'category', 'cat2': 'category', 'cat3': 'category', 'number1': 'numerical', 'number2': 'numerical', 'number3': 'numerical'}
        

        【讨论】:

          【解决方案7】:
          list_ = ['cat1', 'cat2', 'cat3', 'number1', 'number2', 'number3']
          # Don't name the variable "list" as it is a keyword if you can't think of anything else append a underscore at end
          
          my_dict = {}
          
          for item in list_:
              if "cat" in item:
                  my_dict[item] = 'categorical'
              elif "number" in item:
                  my_dict[item] = 'numerical'
          
          print(my_dict)
          

          【讨论】:

            【解决方案8】:
            import itertools
            lst = [‘cat1’, ‘cat2’, ‘cat3’, ‘number1’, ‘number2’, ‘number3’]
            values = [‘categorical’, ‘numerical’]
            
            dict(filter(lambda item: item[0][:3] == item[1][:3], list(itertools.product(lst, values))))
            

            【讨论】:

              猜你喜欢
              • 1970-01-01
              • 2021-01-26
              • 2019-03-12
              • 2019-01-23
              • 1970-01-01
              • 1970-01-01
              • 2020-11-04
              • 2017-12-20
              • 2021-04-15
              相关资源
              最近更新 更多