mylist = 3, 2, 2, 1
mylist = list(set(mylist))
mylist = dict(zip(mylist, mylist)).values()
К сожалению они не только удаляют повторяющиеся элементы но и сортируют сам список

Исходный список: mylist = 3, 2, 2, 1
Необходимый результат: 3, 2, 1

def unique(lst): seen = set() result = [] for x in lst: if x in seen: continue seen.add(x) result.append(x) return result
def unique(lst): seen = set() return zip(*[(x, seen.add(x)) for x in lst if x not in seen])[0]
>>> from collections import OrderedDict >>> mylist = 3, 2, 2, 1 >>> d = OrderedDict.fromkeys(mylist,None) >>> new_list = d.keys() >>> new_list [3, 2, 1]
>>> collect = set() >>> new_list = [e for e in mylist if e not in collect and not collect.add(e)] >>> new_list [3, 2, 1]
>>> print collect.add(1)
None
>>> print collect.add(10)
None
>>> not None
True
EBFEПочему, интересные варианты
Edit: опоздал


and (collect.add(e) or True)
import timeit import random from collections import OrderedDict def bench_set_loop(lst): seen = set() result = [] for x in lst: if x in seen: continue seen.add(x) result.append(x) return result def bench_set_zip(lst): seen = set() return zip(*[(x, seen.add(x)) for x in lst if x not in seen])[0] def bench_set_compr(lst): seen = set() return [e for e in lst if e not in seen and not seen.add(e)] def bench_od(lst): d = OrderedDict.fromkeys(mylist,None) return d.keys() N = 10000 for elements in (10, 100, 1000): mylist = [random.randint(0, 20) for i in range(elements)] print elements, len(set(mylist)) for name, func in [(k, v) for k, v in globals().items() if k.startswith('bench')]: print " %-20s %s" % (name, timeit.timeit(lambda: func(mylist), number=N))
10 9
bench_set_zip 0.0524770499977
bench_set_loop 0.0440655407095
bench_od 0.297880415579
bench_set_compr 0.0362228060105
100 21
bench_set_zip 0.146828339709
bench_set_loop 0.133538776531
bench_od 1.10920786354
bench_set_compr 0.117137887161
1000 21
bench_set_zip 0.695040802332
bench_set_loop 0.687664888766
bench_od 8.29270173866
bench_set_compr 0.666427844187
def unique(lst): seen = set() result = [] for x in lst: if x in seen: continue seen.add(x) result.append(x) return result
>>> collect = set() >>> new_list = [e for e in mylist if e not in collect and not collect.add(e)] >>> new_list [3, 2, 1]
odnochlenНе, грязновато из-за этакого неявного побочного эффекта.
EBFE, ленивые вычисления используешь? Для функциональных языков - нормально, для питона - действительно грязновато


def bench_discard_set(lst): coll = set(lst) return [e for e in lst if e in coll and not coll.discard(e)] def bench_filter(lst): coll = set() return filter(lambda e: e not in coll and not coll.add(e), lst) 10 9 bench_od 0.405310646121 bench_set_compr 0.033174696845 bench_set_zip 0.0523766024844 bench_filter 0.0495791956387 bench_set_loop 0.0485148183261 bench_discard_set 0.0392787948708 100 21 bench_od 1.3885027233 bench_set_compr 0.113566557072 bench_set_zip 0.151898768286 bench_filter 0.23770336247 bench_set_loop 0.147533089046 bench_discard_set 0.157861975861 1000 21 bench_od 9.86658521197 bench_set_compr 0.642895445043 bench_set_zip 0.692988929321 bench_filter 1.80101418028 bench_set_loop 0.722098975156 bench_discard_set 1.11761196075
EBFEПравильность не зависит, зависит скорость.
Кстати - от “ленивости” правильность выполнения не зависит - все будет нормально работать, даже если “collect.add” будет каждый раз вызыватся.
tfoxМожно сказать, что она есть (см. OrderedDict).
Думал, что для такой тривиальной задачи имеется стандартная питоновская функция
>>> collect = set() >>> new_list = [e for e in mylist if e not in collect and not collect.add(e)] >>> new_list [3, 2, 1]