2015-06-15 2 views
1

Попытки соответствовать ключевым, значению в словарях с вложенными элементами спискаСравнить словарь ключа, значение с вложенными элементами списка - Python

dict = {'a':[1, 5], 'c':[7, 9], 'f':[10, 12], 'b':[15, 20]} 
list_A = [['a', '4'], ['a', '7'], ['b', '17'], ['b', 10], ['c', '7'], ['d', '7'], ['f', '11'], ['f', '12']] 
list_A_no_reps =['a', 'b', 'c', 'd', 'f'] 

я пытаюсь получить список, который имеет значение, которые соответствуют с list_A и Dict т.е. как в значениях списка a (вторых элементов во вложенных списках) должно находиться между парой значений списка dict.

match_list = [['a', '4'], ['b', '17'], ['c', '7'], ['f', '11'], ['f', '12']]

Я пытаюсь первым матчем ключей Dict с list_A_no_reps и если есть совпадение, я пытаюсь выяснить, если она лежит между значениями каждого ключа, пары значений. У меня это до сих пор:

g = [] 
for key, values in dict.items(): 
    for element in list_A_no_rep: 
     if key == element: 
     for cord in list_A: 
      if (values[0] <= int(cord[1]) <= values[2]): 
       g.append(cord) 

ответ

1

Я бы сгруппировал подсписки в dict первым элементом, который является буквой, затем перебирает ваш оригинальный dict и проверяет, есть ли каждый ключ в группировке dict и сравнивает вас.

d = {'a': [1, 5], 'c': [7, 9], 'f': [10, 12], 'b': [15, 20]} 

list_A = [['a', '4'], ['a', '7'], ['b', '17'], ['b', 10], ['c', '7'], ['d', '7'], ['f', '11'], ['f', '12']] 

from collections import defaultdict 

d2 = defaultdict(list) 

for k,v in list_A: 
    d2[k].append(v) 

out = [] 
for k, v in d.items(): 
    if k in d2: 
     vals = d2[k] 
     for v2 in vals: 
      if v[0] <= int(v2) <= v[1]: 
       out.append([k,v2]) 
print(out) 
['a', '4'], ['c', '7'], ['b', '17'], ['f', '11'], ['f', '12']] 

Или используйте viewkeys, чтобы получить общие ключи:

out = [] 
for k in d.viewkeys() & d2.viewkeys(): 
    vals, v = d2[k], d[k] 
    for v2 in vals: 
     if v[0] <= int(v2) <= v[1]: 
      out.append([k,v2]) 

Или просто перебираем lišta:

d = {'a': [1, 5], 'c': [7, 9], 'f': [10, 12], 'b': [15, 20]} 

list_A = [['a', '4'], ['a', '7'], ['b', '17'], ['b', 10], ['c', '7'], ['d', '7'], ['f', '11'], ['f', '12']] 

out = [] 
for sub in list_A: 
    k, val = sub 
    if k in d: 
     v = d[k] 
     if v[0] <= int(val) <= v[1]: 
      out.append(sub) 
print(out) 
[['a', '4'], ['b', '17'], ['c', '7'], ['f', '11'], ['f', '12']] 
0

Update

Изменение values[2] в values[1]

Как ваш словарь состоит из двух элементов и индексации с нуля, так что [1, 5] приведет values[0] == 1 and values[1] == 5

Также вы можете пойти на лучшее решение, оставив list_A_no_reps и удаляя if key == element, затем используйте cord[0] для сравнения.

2

Вы можете попробовать:

g = [] 
for key, values in dict.items(): 
    if key in list_A_no_rep: 
     for cord in list_A: 
     if (cord[0] == key): 
       if (values[0] <= int(cord[1]) <= values[1]): 
        g.append(cord) 
print g 

Выход:

[['a', '4'], ['c', '7'], ['b', '17'], ['f', '11'], ['f', '12']] 

Изменение в коде:

g = [] 
for key, values in dict.items(): 
    for element in list_A_no_rep: 
     if key == element: 
      for cord in list_A: 
       if (cord[0] == element): #line added 
        if (values[0] <= int(cord[1]) <= values[1]): 
         g.append(cord) 

Проблема в вашем коде, что вы проверяли со всеми другими элементами list_A тоже. Поэтому вы получите нежелательное значение, которое может быть в диапазоне диапазона другого ключа. Таким образом, условие if необходимо проверить, существует ли допустимое сравнение с тем же ключом.

Например, без условия, которое вы бы проверили ['a','7'] с c:[7,9]. Следовательно, вы включили бы его в g, хотя он не удовлетворяет диапазону, указанному для a.

+0

Идеальное объяснение! – quarters

0
d = {'a':[1, 5], 'c':[7, 9], 'f':[10, 12], 'b':[15, 20]} 
li = [['a', '4'], ['a', '7'], ['b', '17'], ['b', 10], ['c', '7'], ['d', '7'], ['f', '11'], ['f', '12']] 

Было бы быстрее, чтобы найти ключ в d для каждого набора значений в li чем перебирать список для каждого ключа в d.Это может быть сделано в одной строке с list comprehension:

match_li = [v for v in li if v[0] in d and d[v[0]][0] <= int(v[1]) <= d[v[0]][2]] 

дает

[['a', '4'], ['b', '17'], ['c', '7'], ['f', '11'], ['f', '12']]