Поиск уникальных максимальных значений в списке с помощью Python - PullRequest
1 голос
/ 12 марта 2010

У меня есть список точек, как показано ниже

points=[ [x0,y0,v0],  [x1,y1,v1],  [x2,y2,v2].......... [xn,yn,vn]]

Некоторые точки имеют повторяющиеся значения x, y. То, что я хочу сделать, это извлечь уникальное максимальное значение x, y точек

Например, если у меня есть баллы [1,2,5] [1,1,3] [1,2,7] [1,7,3]

Я хотел бы получить список [1,1,3] [1,2,7] [1,7,3]

Как я могу сделать это в Python?

Спасибо

Ответы [ 3 ]

8 голосов
/ 12 марта 2010

Например:

import itertools

def getxy(point): return point[:2]

sortedpoints = sorted(points, key=getxy)

results = []

for xy, g in itertools.groupby(sortedpoints, key=getxy):
  results.append(max(g, key=operator.itemgetter(2)))

, то есть: сортируйте и группируйте точки по xy, для каждой группы с фиксированным xy выберите точку с максимальным z. Кажется простым, если вам удобнее использовать itertools (и это должно быть, это действительно очень мощный и полезный модуль!).

В качестве альтернативы вы могли бы создать dict с (x,y) кортежами в качестве ключей и списками z в качестве значений и сделать один последний проход для этого, чтобы выбрать максимум z для каждого (x, y), но я думаю, что сортировка подход с использованием групп и групп предпочтителен (если, конечно, у вас много миллионов точек, так что производительность сортировки по принципу «большой-O» беспокоит вас в целях масштабируемости, я думаю).

0 голосов
/ 12 марта 2010

Если я понимаю ваш вопрос .. возможно используйте словарь для отображения (x,y) на максимум z

как то так (не проверено)

dict = {}
for x,y,z in list
    if dict.has_key((x,y)):
        dict[(x,y)] = max(dict[(x,y)], z)
    else:
        dict[(x,y)] = z

Хотя заказ будет потерян

0 голосов
/ 12 марта 2010

Вы можете использовать dict для достижения этой цели, используя свойство , что «Если данный ключ просматривается более одного раза, последнее значение, связанное с ним, сохраняется в новом словаре». Этот код сортирует точки, чтобы удостовериться, что самые высокие значения приходят позже, создает словарь, ключи которого являются кортежем первых двух значений, а значение является третьей координатой, а затем переводит его обратно в список

points = [[1,2,5], [1,1,3], [1,2,7], [1,7,3]]
sp = sorted(points)
d = dict( ( (a,b), c) for (a,b,c) in sp)
results = [list(k) + [v] for (k,v) in d.iteritems()]

Может быть способ еще улучшить это, но он удовлетворяет всем вашим требованиям.

...