我想定义一个没有初始化长度的二维数组,如下所示:
Matrix = [][]
但这不起作用...
我已经尝试过下面的代码,但是它也是错误的:
Matrix = [5][5]
错误:
Traceback ...
IndexError: list index out of range
我怎么了
我想定义一个没有初始化长度的二维数组,如下所示:
Matrix = [][]
但这不起作用...
我已经尝试过下面的代码,但是它也是错误的:
Matrix = [5][5]
错误:
Traceback ...
IndexError: list index out of range
我怎么了
Answers:
从技术上讲,您正在尝试索引未初始化的数组。您必须先使用列表初始化外部列表,然后再添加项目。Python将其称为“列表理解”。
# Creates a list containing 5 lists, each of 8 items, all set to 0
w, h = 8, 5;
Matrix = [[0 for x in range(w)] for y in range(h)]
Matrix[0][0] = 1
Matrix[6][0] = 3 # error! range...
Matrix[0][6] = 3 # valid
请注意,矩阵是“ y”地址主地址,换句话说,“ y索引”位于“ x索引”之前。
print Matrix[0][0] # prints 1
x, y = 0, 6
print Matrix[x][y] # prints 3; be careful with indexing!
尽管您可以根据需要命名它们,但是如果您对内部列表和外部列表都使用“ x”,并且希望使用非平方矩阵,那么我会以这种方式来避免索引可能引起的混淆。
range
直接创建内部列表:[range(5) for x in range(5)]
[0] * w
部分很好,但是[[0] * w] * h]
会产生意外的行为。尝试mat = [[0] * 3] * 3; mat[0][1] = 10; print(mat == [[0, 10, 0], [0, 10, 0], [0, 10, 0]])
和mat = [[0] * 3 for i in range(3)]; mat[0][1] = 10; print(mat == [[0, 10, 0], [0, 0, 0], [0, 0, 0]])
。
如果您确实需要矩阵,最好使用numpy
。在numpy
大多数情况下,矩阵运算使用具有二维的数组类型。有很多方法可以创建一个新数组。最有用的zeros
函数之一是函数,它采用shape参数并返回给定形状的数组,其值初始化为零:
>>> import numpy
>>> numpy.zeros((5, 5))
array([[ 0., 0., 0., 0., 0.],
[ 0., 0., 0., 0., 0.],
[ 0., 0., 0., 0., 0.],
[ 0., 0., 0., 0., 0.],
[ 0., 0., 0., 0., 0.]])
这是创建二维数组和矩阵的其他一些方法(为了紧凑起见,删除了输出):
numpy.arange(25).reshape((5, 5)) # create a 1-d range and reshape
numpy.array(range(25)).reshape((5, 5)) # pass a Python range and reshape
numpy.array([5] * 25).reshape((5, 5)) # pass a Python list and reshape
numpy.empty((5, 5)) # allocate, but don't initialize
numpy.ones((5, 5)) # initialize with ones
numpy
也提供了一种matrix
类型,但是不再建议将其用于任何用途,以后可能会删除numpy
它。
np.matrix
它来表示它。用numpy表示矩阵的正确方法是使用array
。
array
s而不是矩阵。尽管并不总是鼓励这样做,但是使用matrix
上下文有合理的理由。
matrix
吗?自从@
引入operator以来,自写这篇文章以来似乎没有什么理由了。
这是用于初始化列表列表的简短表示法:
matrix = [[0]*5 for i in range(5)]
不幸的是,将其缩短为类似的方法5*[5*[0]]
实际上是行不通的,因为最终您会得到同一列表的5个副本,因此,当您修改其中一个副本时,它们都会更改,例如:
>>> matrix = 5*[5*[0]]
>>> matrix
[[0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0]]
>>> matrix[4][4] = 2
>>> matrix
[[0, 0, 0, 0, 2], [0, 0, 0, 0, 2], [0, 0, 0, 0, 2], [0, 0, 0, 0, 2], [0, 0, 0, 0, 2]]
[0]*5
?
[[0]*5 for _ in range(5)]
匿名循环计数器你不使用
[0]*5
正常工作。现在我明白了为什么[{0}]*8
这也是一个坏主意。
如果只需要一个二维容器来容纳某些元素,则可以方便地使用字典:
Matrix = {}
然后,您可以执行以下操作:
Matrix[1,2] = 15
print Matrix[1,2]
这是有效的,因为它1,2
是一个元组,并且您将其用作索引字典的键。结果类似于哑的稀疏矩阵。
如osa和Josap Valls所指出的,您也可以使用,Matrix = collections.defaultdict(lambda:0)
以便丢失的元素具有默认值0
。
Vatsal进一步指出,该方法对于大型矩阵可能不是很有效,并且仅应在代码的非关键性能部分中使用。
import collections; Matrix = collections.defaultdict(float)
,用零代替未初始化的元素。
在Python中,您将创建一个列表列表。您不必提前声明尺寸,但是可以声明。例如:
matrix = []
matrix.append([])
matrix.append([])
matrix[0].append(2)
matrix[1].append(3)
现在,matrix [0] [0] == 2和matrix [1] [0] ==3。您还可以使用列表理解语法。此示例两次使用它来构建“二维列表”:
from itertools import count, takewhile
matrix = [[i for i in takewhile(lambda j: j < (k+1) * 10, count(k*10))] for k in range(10)]
extend
在第一种情况下也会有帮助:如果您以开头m = [[]]
,则可以使用添加到内部列表(扩展行)m[0].extend([1,2])
,并使用添加到外部列表(添加新行)m.append([3,4])
,这些操作将使您离开[[1, 2], [3, 4]]
。
您应该列出列表,最好的方法是使用嵌套的理解:
>>> matrix = [[0 for i in range(5)] for j in range(5)]
>>> pprint.pprint(matrix)
[[0, 0, 0, 0, 0],
[0, 0, 0, 0, 0],
[0, 0, 0, 0, 0],
[0, 0, 0, 0, 0],
[0, 0, 0, 0, 0]]
在您的[5][5]
示例中,您正在创建一个内部带有整数“ 5”的列表,并尝试访问其第五项,这自然会引发IndexError,因为没有第五项:
>>> l = [5]
>>> l[5]
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
IndexError: list index out of range
rows = int(input())
cols = int(input())
matrix = []
for i in range(rows):
row = []
for j in range(cols):
row.append(0)
matrix.append(row)
print(matrix)
为什么这么长的代码,Python
您也会问?
很久以前,当我不熟悉Python时,我看到了编写2D矩阵的单行答案,并告诉自己我不再打算在Python中再次使用2D矩阵。(这些行很吓人,它没有给我有关Python所做的任何信息。还要注意,我不知道这些速记法。)
无论如何,这是一个来自C,CPP和Java背景的初学者的代码
给Python爱好者和专家的说明:请不要因为我编写了详细的代码而投了反对票。
重写以便于阅读:
# 2D array/ matrix
# 5 rows, 5 cols
rows_count = 5
cols_count = 5
# create
# creation looks reverse
# create an array of "cols_count" cols, for each of the "rows_count" rows
# all elements are initialized to 0
two_d_array = [[0 for j in range(cols_count)] for i in range(rows_count)]
# index is from 0 to 4
# for both rows & cols
# since 5 rows, 5 cols
# use
two_d_array[0][0] = 1
print two_d_array[0][0] # prints 1 # 1st row, 1st col (top-left element of matrix)
two_d_array[1][0] = 2
print two_d_array[1][0] # prints 2 # 2nd row, 1st col
two_d_array[1][4] = 3
print two_d_array[1][4] # prints 3 # 2nd row, last col
two_d_array[4][4] = 4
print two_d_array[4][4] # prints 4 # last row, last col (right, bottom element of matrix)
采用:
matrix = [[0]*5 for i in range(5)]
第一维的* 5起作用是因为在此级别上,数据是不可变的。
matrix = [[0]*cols for _ in range(rows)]
声明零(一)矩阵:
numpy.zeros((x, y))
例如
>>> numpy.zeros((3, 5))
array([[ 0., 0., 0., 0., 0.],
[ 0., 0., 0., 0., 0.],
[ 0., 0., 0., 0., 0.]])
或numpy.ones((x,y))例如
>>> np.ones((3, 5))
array([[ 1., 1., 1., 1., 1.],
[ 1., 1., 1., 1., 1.],
[ 1., 1., 1., 1., 1.]])
甚至三个尺寸都是可能的。(http://www.astro.ufl.edu/~warner/prog/python.html参见->多维数组)
使用NumPy,您可以像这样初始化空矩阵:
import numpy as np
mm = np.matrix([])
然后像这样追加数据:
mm = np.append(mm, [[1,2]], axis=1)
如果您希望能够将其视为2D数组,而不是被迫以列表列表的方式思考(我认为这自然得多),则可以执行以下操作:
import numpy
Nx=3; Ny=4
my2Dlist= numpy.zeros((Nx,Ny)).tolist()
结果是一个列表(不是NumPy数组),您可以用数字,字符串或其他内容覆盖各个位置。
numpy.matrix
相当于numpy.zeros
无零而不列表?
matrix = {}
您可以通过两种方式定义键和值:
matrix[0,0] = value
要么
matrix = { (0,0) : value }
结果:
[ value, value, value, value, value],
[ value, value, value, value, value],
...
采用:
import copy
def ndlist(*args, init=0):
dp = init
for x in reversed(args):
dp = [copy.deepcopy(dp) for _ in range(x)]
return dp
l = ndlist(1,2,3,4) # 4 dimensional list initialized with 0's
l[0][1][2][3] = 1
我确实认为NumPy是要走的路。如果您不想使用NumPy,则以上是一种通用方法。
通过使用列表:
matrix_in_python = [['Roy',80,75,85,90,95],['John',75,80,75,85,100],['Dave',80,80,80,90,95]]
通过使用dict:您还可以将此信息存储在哈希表中,以进行快速搜索,例如
matrix = { '1':[0,0] , '2':[0,1],'3':[0,2],'4' : [1,0],'5':[1,1],'6':[1,2],'7':[2,0],'8':[2,1],'9':[2,2]};
matrix ['1']将为您提供O(1)时间的结果
* nb:您需要处理哈希表中的冲突
如果在开始之前没有尺寸信息,请创建两个一维列表。
list 1: To store rows
list 2: Actual two-dimensional matrix
将整个行存储在第一个列表中。完成后,将列表1附加到列表2:
from random import randint
coordinates=[]
temp=[]
points=int(raw_input("Enter No Of Coordinates >"))
for i in range(0,points):
randomx=randint(0,1000)
randomy=randint(0,1000)
temp=[]
temp.append(randomx)
temp.append(randomy)
coordinates.append(temp)
print coordinates
输出:
Enter No Of Coordinates >4
[[522, 96], [378, 276], [349, 741], [238, 439]]
# Creates a list containing 5 lists initialized to 0
Matrix = [[0]*5]*5
请注意此简短表达,请参见@FJ答案中的完整解释
Matrix[0], Matrix[1], ..., Matrix[4]
所有都指向同一个数组,所以之后Matrix[0][0] = 3
,您将期望Matrix[0][0] == Matrix[1][0] == ... == Matrix[4][0] == 3
。
l=[[0]*(L) for _ in range(W)]
将比:
l = [[0 for x in range(L)] for y in range(W)]
[[0]*(L) for i in range(W)]
应该是[[0]*(L) for _ in range(W)]
因为i
没有在任何地方使用
尝试这个:
rows = int(input('Enter rows\n'))
my_list = []
for i in range(rows):
my_list.append(list(map(int, input().split())))
这是在python中创建矩阵的代码片段:
# get the input rows and cols
rows = int(input("rows : "))
cols = int(input("Cols : "))
# initialize the list
l=[[0]*cols for i in range(rows)]
# fill some random values in it
for i in range(0,rows):
for j in range(0,cols):
l[i][j] = i+j
# print the list
for i in range(0,rows):
print()
for j in range(0,cols):
print(l[i][j],end=" ")
如果我错过了什么,请提出建议。