2013-07-17 7 views
1

Извините, я довольно новичок в python, но мне нужно было взять 6 отдельных списков и объединить их так, чтобы они были похожи на список списков.Почему я не могу перебирать список списков таким образом?

т.е. a1 из списка A + b1 из списка B + c1 из списка C и a2 из списка А + b2 .... и т.д.

должен стать [[a1, b1, c1], [a2, b2, c2] ...]

Я попытался это:

combList = [[0]*6]*len(lengthList) 

for i in range(len(lengthList)): 
    print i 
    combList[i][0] = posList[i] 
    combList[i][1] = widthList[i] 
    combList[i][2] = heightList[i] 
    combList[i][3] = areaList[i] 
    combList[i][4] = perimList[i] 
    combList[i][5] = lengthList[i] 
    # i++ 
print combList 

, а затем попробовал вариант, в котором я прилагаемую вместо:

for i in range(len(lengthList)): 
     print i 
     combList[i][0].append(posList[i]) 
     combList[i][1].append(widthList[i]) 
     combList[i][2].append(heightList[i]) 
     combList[i][3].append(areaList[i]) 
     combList[i][4].append(perimList[i]) 
     combList[i][5].append(lengthList[i]) 
     # i++ 
    print combList 

Итак, у меня есть два вопроса.

Почему ни один из них не работал, как мне кажется. И мне не нужно ставить i ++ внизу справа? По какой-то причине он просто не работал, поэтому я просто стрелял.

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

for j in range(len(fNameList)): 
      rows = [fNameList[j], widthList[j], heightList[j], areaList[j], perimeterList[j], lengthList[j]] 
      print rows 
      combList.append(rows) 
     print combList 

ответ

4

Проблема с вами в том, что вы создаете список из 6 ссылок на одно и то же.

[0]*6 сгенерирует список из 6 ссылок на то же число (ноль), и [[0]*6]*len(lengthList) сгенерирует список ссылок на тот же список [0]*6.

Я думаю, что функция, которую вы хотите, zip:

A = ['a1','a2','a3'] 
B = ['b1','b2','b3'] 
C = ['c1','c2','c3'] 

print [x for x in zip(A,B,C)] 

, который дает:

[('a1', 'b1', 'c1'), ('a2', 'b2', 'c2'), ('a3', 'b3', 'c3')] 

Так что в вашем случае, это будет работать:

combList = [x for x in zip(fNameList, widthList, heightList, areaList, perimeterList, lengthList)] 
3

Вы делаете список names все указатели на тот же список из шести нулей, когда вы делаете:

combList = [[0]*6]*len(lengthList) 

Это равносильно тому, как это сделать:

internal_list = [0] * 6 
combList = [internal_list, internal_list, internal_list, internal_list, internal_list] 

Вместо этого, если вы используете zip вы можете получить то, что вы хотите за один проход:

zipped_list = zip(posList, widthList, heightList, areaList, perimList, lengthList) 
+0

я вижу! Большое вам спасибо. Никогда не знал о «именах» python, и я думал, что zip должен был просто объединить 2 списка в кортежи, но теперь я знаю. – loonyuni

3

a = [0]*6 определяет список с 6 ссылки, все эти ссылки указывают на число 0

[a]*m определяет список с m ссылками, все указывающие на a, в данном случае [0]*6.

Код в вашем последнем примере работает, потому что он добавляет ссылки на новые объекты, а не на изменение существующего.

Другие пользователи рекомендуют использовать zip, и это действительно лучшее решение, ИМХО.

1

Вы могли бы сделать это с пониманием через молнию, если списки все же длины

[list(tup) for tup in zip (l1, l2, l3...)] 
1

В зависимости от версии Python и насколько велик ваш 3 списка вы должны использовать либо zip или izip.

izip если вы используете Python < 3 (вы можете использовать zip как хорошо, но если эти списки очень большие, то генератор будет целая куча быстрее и лучше для вас).

zip если вы работаете Python> = 3

from itertools import izip 

zipped_list = izip(a,b,c) 

for item in zipped_list: 
    print item 
>> (1, 1, 1) 
>> (2, 2, 2) 
>> (3, 3, 3) 
>> (4, 4, 4) 
>> (5, 5, 5) 

И только для бита обучающимся о том, как написать хороший чистый глядя Python:

Ваш цикл, который вы сделали for i in range(len(lengthList) может очень легко трансформироваться в то, что действительно является Pythonic.

for item in lengthList: 

Теперь вы думаете: «Как насчет моего индекса, я не могу получить доступ к индексу элемента». Ну Python есть исправление, что тоже называется enumerate и использовать его так:

for index, item in enumerate(lengthlist): 

Так перевод кода вниз к более вещий синтаксис:

for index, element in enumerate(lengthList): 
    combList[index][0].append(posList[index]) 
    combList[index][1].append(widthList[index]) 
    combList[index][2].append(heightList[index]) 
    combList[index][3].append(areaList[index]) 
    combList[index][4].append(perimList[index]) 
    combList[index][5].append(lengthList[index]) 
Смежные вопросы