цикл по списку словарей

1

У меня есть список словарей. в списке есть несколько точек, некоторые из них несколько. Когда есть множественная запись, я хочу рассчитать среднее значение x и y этой точки. Моя проблема в том, что я не знаю, как перебирать список словарей для сравнения идентификаторов точек!

когда я использую что-то вроде этого:

for i in list:
  for j in list:
    if i['id'] == j['id']:
      point = getPoint(i['geom'])
      ....

Извините, формация немного сложна... вторая петля внутри первой... Я думаю, что он сравнивает первую запись списка, поэтому он тот же... так что мне нужно начинать во втором цикле со второй записи, но я не могу сделать это с i-1, потому что я - словарь словаря... У кого-то есть идея? спасибо заранее!

 for j in range(1, len(NEWPoint)):
      if i['gid']==j['gid']:
         allsamePoints.append(j)
      for k in allsamePoints:
         for l in range(1, len(allsamePoints)):
            if k['gid']==l['gid']:
                Point1 = k['geom']
                Point2=l['geom']
                X=(Point1.x()+Point2.x())/2
                Y=(Point1.y()+Point2.y())/2
                AVPoint = QgsPoint(X, Y)
                NEWReturnList.append({'gid': j['gid'], 'geom': AVPoint})
                del l
      for m in NEWReturnList:
          for n in range(1, len(NEWReturnList)):
              if m['gid']==n['gid']:
                 Point1 = m['geom']
                 Point2=n['geom']
                 X=(Point1.x()+Point2.x())/2
                 Y=(Point1.y()+Point2.y())/2
                 AVPoint = QgsPoint(X, Y)
                 NEWReturnList.append({'gid': j['gid'], 'geom': AVPoint})
                 del n
              else:
                 pass

ОК, я думаю... на данный момент это более запутанно:)...

  • 0
    Какой язык вы используете?
  • 0
    я использую питон
Показать ещё 6 комментариев
Теги:
loops
dictionary

2 ответа

4

Один из способов - изменить способ хранения ваших очков, потому что, как вы уже заметили, трудно получить то, что вы хотите от него.

Более полезной структурой будет dict, где id отображает список точек:

from collections import defaultdict
points_dict = defaultdict(list)

# make the new dict
for point in point_list:
    id = point["id"]
    points_dict[id].append(point['geom'])

def avg( lst ):
    """ average of a `lst` """
    return 1.0 * sum(lst)/len(lst)

# now its simple to get the average
for id in points_dict:
    print id, avg( points_dict[id] )
  • 0
    Я отозвал комментарий, который был в середине написания, так как THC4k верен. Список диктовок вообще не идеален - более естественно, у вас есть ОДИН диктант, в котором вы можете сначала дедуплицировать пункты. +1 Однако, THC4k, было бы неплохо, если бы вы добавили код о том, как создать такой диктат из списка, чтобы сделать его более понятным для ОП.
  • 0
    Итак, когда я иду с points_dict [id] .append (...), я получаю словарь с несколькими элементами с разными идентификаторами и геометриями ?! я хотел сделать это со списком словарей, потому что я не мог найти ничего для хранения нескольких элементов (как в таблице Excel) в словаре ...
Показать ещё 4 комментария
0

Я не совсем уверен, что вы хотите сделать, но я думаю, что фильтрация списка поможет вам. Там встроенная функция filter, которая выполняет итерацию по последовательности и для каждого элемента вызывает пользовательскую функцию, чтобы определить, включать ли этот элемент в результирующий список или нет.

Например:

def is4(number):
   return number == 4

l = [1, 2, 3, 4, 5, 6, 4, 7, 8, 4, 4]
filter(is4, l) # returns [4, 4, 4, 4]

Итак, имея список словарей, чтобы отфильтровать все словари с определенной записью, равной заданному значению, вы можете сделать что-то вроде этого:

def filter_dicts(dicts, entry, value):
   def filter_function(d):
      if entry not in d:
         return False
      return d[entry] == value
   return filter(filter_function, dicts)

С помощью этой функции, чтобы все словари с записью "id" равны 2, вы можете сделать:

result = filter_dicts(your_list, "id", 2)

С этим ваш основной цикл может выглядеть примерно так:

processed_ids = set()
for item in list:
   id = item['id']
   if id in processed_ids:
      continue
   processed_ids.add(id)
   same_ids = filter_dicts(list, "id", id)
   # now do something with same_ids

Надеюсь, я правильно понял вас и что это вам полезно.

  • 0
    о, круто!!! спасибо большое ... это выглядит хорошо ... я должен прочитать это снова и попробовать это с моим!
  • 0
    это работает! Джипи!

Ещё вопросы

Сообщество Overcoder
Наверх
Меню