2014-09-17 2 views
0

В попытке выбрать первый (если считать от нуля) столбца в 2D массив 4x4, я написал следующий скрипт:Выбор столбца из массива в Python

import numpy 
a4x4=[list(range(4*i,4*(i+1))) for i in list(range(4))] 
print(a4x4) 
print(a4x4[:,1]) 

Массив, кажется, в порядке:

[[0, 1, 2, 3], [4, 5, 6, 7], [8, 9, 10, 11], [12, 13, 14, 15]] 

но вместо

[1, 5, 9, 13]

для второй печати, я получаю эту ошибку:

TypeError: list indices must be integers, not tuple

Зачем возникает эта ошибка, что происходит не так?

+0

Как примечание стороны, вам не нужны те дополнительные 'list' звонки. 'для i в списке (диапазон (4))' даст вам точные результаты, как только для i в диапазоне (4) ', за исключением того, что он будет тратить время и память на создание списка с теми же элементами, что и диапазон, который вы уже были. – abarnert

+0

А, спасибо. Я помню, что список() был остатком попытки распечатать этот диапазон. – Betohaku

+0

Просто убедившись. Многие люди не понимают, что большая часть Python построена вокруг общих итераций, и нет ничего особенного в списках; такие вещи, как диапазоны, строки, файлы и т. д., являются такими же итерабельными. (С другой стороны, Numpy не строится вокруг итерации, а вокруг операций литья по всем массивам или срезам сразу.) – abarnert

ответ

3

Вы импортируете numpy, но не используете его. У вас есть список списков, и Python не поддерживает многомерную нарезку для этого (т. Е. Вам понадобится [a4x4[i][1] for i in range(4)], чтобы получить ожидаемый результат, но на самом деле вы должны использовать numpy). Вот пример:

import numpy 
a4x4=numpy.array([list(range(4*i,4*(i+1))) for i in list(range(4))]) 
print(a4x4) 
print(a4x4[:,1]) 

Кстати, в NumPy вы также можете создать массив, который вы хотите напрямую, как это:

numpy.arange(4*4).reshape((4,4)) 

(А также в Python один не нуждается в list вызовов У меня выше, я просто стараюсь, чтобы код как можно более похожий на ваш, чтобы увидеть ключевую вещь, которая преобразует список списков в массив numpy.)

+0

Или, конечно, 'np.arange (16) .reshape ((4,4))' , – abarnert

+0

Отлично, я понятия не имел, что нарезка будет работать только на массивах numpy. Почему это различие между списками списков и массивами? – Betohaku

+1

@Betohaku: нарезка работает как на массивах numples, так и на списках; просто * многомерная * нарезка работает только на массивах numpy. – tom10

1

Вы можете создать результат, который хотите использовать список - так же, как вы создали оригинал 4x4:

a4x4=[list(range(4*i,4*(i+1))) for i in list(range(4))] 
print([a4x4[i][1] for i in range(4)]) 

Кроме того, вы можете упростить вашу логику немного, бросая из функции list:

a4x4 = [range(4*i,4*(i+1)) for i in range(4)] 
print([a4x4[i][1] for i in range(4)]) 
+0

На самом деле интуитивно понятный подход, но это кажется довольно круговой, особенно потому, что для этого требуется знать размеры массива (что, конечно, в этом примере вы делаете, но представьте себе использование вне этого контекста). – Betohaku

+1

+1, так как этот ответ заставил меня осознать ошибку в моем собственном, но все же, я думаю, что OP хочет использовать numpy вместо списков. – tom10

Смежные вопросы