Як з'єднати два списки в Python?
Приклад:
listone = [1, 2, 3]
listtwo = [4, 5, 6]
Очікуваний результат:
>>> joinedlist
[1, 2, 3, 4, 5, 6]
[1,2,5] and [2,4,5,6]? Ви хочете, щоб дублікати були включені, виключені чи не байдуже?
Як з'єднати два списки в Python?
Приклад:
listone = [1, 2, 3]
listtwo = [4, 5, 6]
Очікуваний результат:
>>> joinedlist
[1, 2, 3, 4, 5, 6]
[1,2,5] and [2,4,5,6]? Ви хочете, щоб дублікати були включені, виключені чи не байдуже?
Відповіді:
Ви можете використовувати +оператор, щоб комбінувати їх:
listone = [1,2,3]
listtwo = [4,5,6]
joinedlist = listone + listtwo
Вихід:
>>> joinedlist
[1,2,3,4,5,6]
listone += listtwoрезультати вlistone == [1, 2, 3, 4, 5, 6]
list3 = listone listone+=listtwo чи змінюється також list3?
Можливо також створити генератор, який просто повторює елементи в обох списках, використовуючи itertools.chain(). Це дозволяє ланцюжка списків (або будь-яких ітерабельних) разом для обробки без копіювання елементів у новий список:
import itertools
for item in itertools.chain(listone, listtwo):
# Do something with each list item
chainзнаходиться на більш повільній стороні (але не набагато) для двох списків, але це найшвидше рішення для зв'язання декількох списків (n >> 2).
>= 3.5Альтернатива Python :[*l1, *l2]
Ще одна альтернатива була введена, прийняття PEP 448якої заслуговує на згадку.
PEP під назвою " Додаткові розпаковувальні узагальнення" , як правило, зменшував деякі синтаксичні обмеження при використанні зірочного *вираження в Python; з нею тепер об'єднання двох списків (стосується будь-якого ітерабельного):
>>> l1 = [1, 2, 3]
>>> l2 = [4, 5, 6]
>>> joined_list = [*l1, *l2] # unpack both iterables in a list literal
>>> print(joined_list)
[1, 2, 3, 4, 5, 6]
Ця функціональність була визначена для Python,3.5 вона не підтримувалась у попередніх версіях у 3.xродині. У непідтримуваних версіях A SyntaxErrorбуде піднято.
Як і в інших підходах, це теж створює дрібну копію елементів у відповідних списках.
Перевернуте цей підхід полягає в тому , що ви дійсно не потрібно списках для того , щоб виконати це, все , що ітератор буде робити. Як зазначено в ПЕП:
Це також корисно як більш читабельний спосіб підбиття ітерабелів до списку, такого,
my_list + list(my_tuple) + list(my_range)який зараз еквівалентний справедливому[*my_list, *my_tuple, *my_range].
Отже, хоча додавання з +би призвело TypeErrorдо невідповідності типу:
l = [1, 2, 3]
r = range(4, 7)
res = l + r
Наступне не буде:
res = [*l, *r]
тому що він спочатку розпакує вміст ітерабелів, а потім просто створить listзі змісту.
res = [*l1, *reversed(l2)]. Оскільки reversedповертає ітератор, res = l1 + reversed(l2)він видасть помилку.
Ви можете використовувати набори для отримання об'єднаного списку унікальних значень
mergedlist = list(set(listone + listtwo))
listone + [x for x in listtwo if x not in listone]
import collections; mergedlist = list(collections.OrderedDict.fromkeys(listone + listtwo))зробите свою справу.
Ви також можете скористатися list.extend()методом, щоб додати a listдо кінця іншого:
listone = [1,2,3]
listtwo = [4,5,6]
listone.extend(listtwo)
Якщо ви хочете зберегти оригінальний список недоторканим, ви можете створити новий listоб’єкт та extendобидва списки до нього:
mergedlist = []
mergedlist.extend(listone)
mergedlist.extend(listtwo)
Як з'єднати два списки в Python?
Станом на 3.7, це найпопулярніші методи stdlib для об'єднання двох (або більше) списків у python.
Виноски
Це гладке рішення через його лаконічність. Але
sumвиконує конкатенацію попарно, це означає, що це квадратична операція, оскільки для кожного кроку потрібно виділяти пам'ять. НЕ ВИКОРИСТОВУЙТЕ, якщо ваші списки великі.Див.
chainІchain.from_iterableз док. Вам потрібноimport itertoolsспочатку. Конкатенація лінійна в пам'яті, тому це найкраще з точки зору продуктивності та сумісності версій.chain.from_iterableбуло введено в 2.6.Цей метод використовує додаткові генерації розпакування (PEP 448) , але не може узагальнити до N списків, якщо ви не розпакуйте кожне вручну самостійно.
a += bіa.extend(b)є більш-менш рівноцінними для всіх практичних цілей.+=при виклику в списку буде внутрішній дзвінокlist.__iadd__, який розширює перший список на другий.
З’єднання в 2 списку 1
Різниця між цими методами не велика, але це має сенс, враховуючи, що всі вони мають однаковий порядок складності (лінійний). Немає особливих причин віддавати перевагу одному над іншим, крім питання стилю.
З'єднання N-списків
Діаграми були створені за допомогою модуля perfplot . Код, для довідки.
1. iadd( +=) та extendметоди діють на місці, тому копія повинна створюватися кожного разу перед тестуванням. Щоб зробити справи справедливими, усі методи мають крок попередньої копії для лівого списку, який можна ігнорувати.
НЕ ВИКОРИСТОВУЙТЕ МЕТОДУ ДУНДЕРУ list.__add__безпосередньо ні в якому разі, формі чи формі. Насправді залишайтеся осторонь методів, а також використовуйте оператори та operatorфункції, як вони були розроблені. Python має ретельну семантику, яка є більш складною, ніж просто виклик кандидата безпосередньо. Ось приклад . Отже, підсумовуючи, a.__add__(b)=> BAD; a + b=> ДОБРО.
Деякі відповіді тут пропонують reduce(operator.add, [a, b])парне конкатенацію - це те саме, що sum([a, b], [])лише багатослівне.
Будь-який метод, який використовує set, скидає копії та втрачає замовлення. Використовуйте обережно.
for i in b: a.append(i)є більш багатослівним і повільнішим, ніж a.extend(b)функція виклику однієї функції та ідіоматичніша. appendповільніше через семантику, з якою пам'ять виділяється та вирощується для списків. Дивіться тут для подібної дискусії.
heapq.mergeбуде працювати, але випадок його використання призначений для об'єднання відсортованих списків у лінійний час. Використання його в будь-якій іншій ситуації є анти-закономірністю.
yieldЯкщо список елементів з функції є прийнятним методом, але chainробить це швидше і краще (у нього є шлях коду до C, тому він швидкий).
operator.add(a, b)є прийнятним функціональним еквівалентом a + b. Це випадки використання в основному для динамічного відправлення методу. В іншому випадку, віддайте перевагу, a + bякий коротший і легший для читання, на мій погляд . YMMV.
"There's not much difference between these methods but that makes sense given they all have the same order of complexity (linear). There's no particular reason to prefer one over the other except as a matter of style."Рішення, не вказані у моїй відповіді, або закинуті в" Коментарі ", я рекомендую не використовувати.
Це досить просто, і я думаю, це навіть було показано в підручнику :
>>> listone = [1,2,3]
>>> listtwo = [4,5,6]
>>>
>>> listone + listtwo
[1, 2, 3, 4, 5, 6]
Це питання безпосередньо задає питання про об'єднання двох списків. Однак це досить високий пошук, навіть коли ви шукаєте спосіб приєднання до багатьох списків (у тому числі, коли ви приєднуєтесь до нульових списків).
Я думаю, що найкращим варіантом є використання розуміння списку:
>>> a = [[1,2,3], [4,5,6], [7,8,9]]
>>> [x for xs in a for x in xs]
[1, 2, 3, 4, 5, 6, 7, 8, 9]
Ви також можете створити генератори:
>>> map(str, (x for xs in a for x in xs))
['1', '2', '3', '4', '5', '6', '7', '8', '9']
Стара відповідь
Розглянемо цей більш загальний підхід:
a = [[1,2,3], [4,5,6], [7,8,9]]
reduce(lambda c, x: c + x, a, [])
Виведе:
[1, 2, 3, 4, 5, 6, 7, 8, 9]
Зауважте, це також працює правильно, коли aє []або [[1,2,3]].
Однак це можна зробити ефективніше itertools :
a = [[1,2,3], [4,5,6], [7,8,9]]
list(itertools.chain(*a))
Якщо вам не потрібен list , а просто ітерабельний, пропустіть list().
Оновлення
Альтернатива, запропонована Патріком Коллінзом у коментарях, також може підійти вам:
sum(a, [])
reduceзараз увімкнено, functoolsтому вам потрібно спочатку імпортувати його.
Ви можете просто скористатися оператором +або +=оператором так:
a = [1, 2, 3]
b = [4, 5, 6]
c = a + b
Або:
c = []
a = [1, 2, 3]
b = [4, 5, 6]
c += (a + b)
Крім того, якщо ви хочете, щоб значення в об'єднаному списку були унікальними, ви можете зробити:
c = list(set(a + b))
list(dict.fromkeys(a + b))
Варто зазначити, що itertools.chainфункція приймає змінну кількість аргументів:
>>> l1 = ['a']; l2 = ['b', 'c']; l3 = ['d', 'e', 'f']
>>> [i for i in itertools.chain(l1, l2)]
['a', 'b', 'c']
>>> [i for i in itertools.chain(l1, l2, l3)]
['a', 'b', 'c', 'd', 'e', 'f']
Якщо вхід є ітерабельним (кортеж, список, генератор тощо), from_iterableможе застосовуватися метод класу:
>>> il = [['a'], ['b', 'c'], ['d', 'e', 'f']]
>>> [i for i in itertools.chain.from_iterable(il)]
['a', 'b', 'c', 'd', 'e', 'f']
З Python 3.3+ ви можете використовувати вихід із :
listone = [1,2,3]
listtwo = [4,5,6]
def merge(l1, l2):
yield from l1
yield from l2
>>> list(merge(listone, listtwo))
[1, 2, 3, 4, 5, 6]
Або, якщо ви хочете підтримати довільну кількість ітераторів:
def merge(*iters):
for it in iters:
yield from it
>>> list(merge(listone, listtwo, 'abcd', [20, 21, 22]))
[1, 2, 3, 4, 5, 6, 'a', 'b', 'c', 'd', 20, 21, 22]
itertools.chain(що еквівалентно) замість визначення власної функції.
Якщо ви хочете об'єднати два списки у відсортованому вигляді, ви можете скористатися mergeфункцією з heapqбібліотеки.
from heapq import merge
a = [1, 2, 4]
b = [2, 4, 6, 7]
print list(merge(a, b))
Якщо ви не можете використовувати оператор плюс ( +), ви можете скористатися operatorімпортом:
import operator
listone = [1,2,3]
listtwo = [4,5,6]
result = operator.add(listone, listtwo)
print(result)
>>> [1, 2, 3, 4, 5, 6]
Крім того, ви також можете використовувати функцію " __add__ Дандер" :
listone = [1,2,3]
listtwo = [4,5,6]
result = list.__add__(listone, listtwo)
print(result)
>>> [1, 2, 3, 4, 5, 6]
+немає за столом, використовуйте operator.add.
Як більш загальний спосіб для більшої кількості списків, ви можете помістити їх у список та використовувати функцію itertools.chain.from_iterable()1, яка ґрунтується на цій відповіді, є найкращим способом розшарування вкладеного списку:
>>> l=[[1, 2, 3], [4, 5, 6], [7, 8, 9]]
>>> import itertools
>>> list(itertools.chain.from_iterable(l))
[1, 2, 3, 4, 5, 6, 7, 8, 9]
1. Зауважте, що chain.from_iterable()це доступно в Python 2.6 та пізніших версіях. В інших версіях використовуйте chain(*l).
Якщо вам потрібно об'єднати два упорядковані списки зі складними правилами сортування, можливо, вам доведеться прокрутити його самостійно, як у наведеному нижче коді (використовуючи просте правило сортування для читабельності :-)).
list1 = [1,2,5]
list2 = [2,3,4]
newlist = []
while list1 and list2:
if list1[0] == list2[0]:
newlist.append(list1.pop(0))
list2.pop(0)
elif list1[0] < list2[0]:
newlist.append(list1.pop(0))
else:
newlist.append(list2.pop(0))
if list1:
newlist.extend(list1)
if list2:
newlist.extend(list2)
assert(newlist == [1, 2, 3, 4, 5])
heapq.merge.
Ви можете використовувати append()метод, визначений на listоб'єктах:
mergedlist =[]
for elem in listone:
mergedlist.append(elem)
for elem in listtwo:
mergedlist.append(elem)
Як вже вказували багато людей, itertools.chain()це шлях, якщо потрібно застосувати однаковий режим до обох списків. У моєму випадку я мав етикетку та прапор, які відрізнялися від одного списку до іншого, тому мені було потрібно щось трохи складніше. Як виявляється, за лаштунками itertools.chain()просто робиться наступне:
for it in iterables:
for element in it:
yield element
(див. https://docs.python.org/2/library/itertools.html ), тому я взяв натхнення звідси і написав щось у цьому напрямку:
for iterable, header, flag in ( (newList, 'New', ''), (modList, 'Modified', '-f')):
print header + ':'
for path in iterable:
[...]
command = 'cp -r' if os.path.isdir(srcPath) else 'cp'
print >> SCRIPT , command, flag, srcPath, mergedDirPath
[...]
Основні моменти, які слід зрозуміти тут, полягають у тому, що списки - це лише окремий випадок ітерабельності, який є об'єктами, як і будь-який інший; і ці for ... inпетлі в python можуть працювати з змінними кортежу, тому просто циклічно працювати на декількох змінних одночасно.
Використовуйте просте розуміння списку:
joined_list = [item for list_ in [list_one, list_two] for item in list_]
Він має всі переваги найновішого підходу використання додаткових розпаковуючих узагальнень - тобто ви можете об'єднати довільну кількість різних ітерабелів (наприклад, списки, кортежі, діапазони та генератори) таким чином - і це не обмежується Python 3.5 або пізнішої версії .
Справді стислий спосіб об’єднати список списків
list_of_lists = [[1,2,3], [4,5,6], [7,8,9]]
reduce(list.__add__, list_of_lists)
що дає нам
[1, 2, 3, 4, 5, 6, 7, 8, 9]
list.__add__, operator.addа використовуйте натомість. Це більш багатослівний еквівалент, sum(list_of_lists, [])який так само поганий. НЕ ВИКОРИСТОВУВАТИ!
obj.__class__і obj.__dict__.
У Python ви можете об'єднати два масиви сумісних розмірів за допомогою цієї команди
numpy.concatenate([a,b])
Тож є два простих способи.
+ : Він створює новий список із наданих списківПриклад:
In [1]: a = [1, 2, 3]
In [2]: b = [4, 5, 6]
In [3]: a + b
Out[3]: [1, 2, 3, 4, 5, 6]
In [4]: %timeit a + b
10000000 loops, best of 3: 126 ns per loop
Приклад:
In [1]: a = [1, 2, 3]
In [2]: b = [4, 5, 6]
In [3]: %timeit a.extend(b)
10000000 loops, best of 3: 91.1 ns per loop
Таким чином, ми бачимо, що з двох найпопулярніших методів extendце ефективно.
chain.from_iterable).
Існує кілька способів об'єднати списки в python.
l1 = [1,2,3,4]
l2 = [3,4,5,6]
1. new_list = l1.extend(l2)
2. new_list = l1 + l2
3. new_list = [*l1, *l2]
import itertools
A = list(zip([1,3,5,7,9],[2,4,6,8,10]))
B = [1,3,5,7,9]+[2,4,6,8,10]
C = list(set([1,3,5,7,9] + [2,4,6,8,10]))
D = [1,3,5,7,9]
D.append([2,4,6,8,10])
E = [1,3,5,7,9]
E.extend([2,4,6,8,10])
F = []
for a in itertools.chain([1,3,5,7,9], [2,4,6,8,10]):
F.append(a)
print ("A: " + str(A))
print ("B: " + str(B))
print ("C: " + str(C))
print ("D: " + str(D))
print ("E: " + str(E))
print ("F: " + str(F))
Вихід:
A: [(1, 2), (3, 4), (5, 6), (7, 8), (9, 10)]
B: [1, 3, 5, 7, 9, 2, 4, 6, 8, 10]
C: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
D: [1, 3, 5, 7, 9, [2, 4, 6, 8, 10]]
E: [1, 3, 5, 7, 9, 2, 4, 6, 8, 10]
F: [1, 3, 5, 7, 9, 2, 4, 6, 8, 10]
Якщо ви хотіли нового списку, зберігаючи два старі списки:
def concatenate_list(listOne, listTwo):
joinedList = []
for i in listOne:
joinedList.append(i)
for j in listTwo:
joinedList.append(j)
sorted(joinedList)
return joinedList
lst1 = [1,2]
lst2 = [3,4]
def list_combinationer(Bushisms, are_funny):
for item in lst1:
lst2.append(item)
lst1n2 = sorted(lst2)
print lst1n2
list_combinationer(lst1, lst2)
[1,2,3,4]
Ви можете слідувати коду
listone = [1, 2, 3]
listtwo = [4, 5, 6]
for i in listone:
listtwo.append(i)
print(listtwo)
[1,2,3,4,5,6]