I have written code which creates matrices with name matrixi
, where i
is replaced with the current loop number:
for i in range(len(node2)):
if sOrP[i] == 'S':
#print('series connection')
matrixTemplate = numpy.array([[1.0, 0.0], [0.0, 1.0]]) #Got to put 1.0 else it doesnt work
matrixTemplate[0][1] = frequenciesList[0][i]
globals()['matrix%s' % i] = matrixTemplate
#print(matrixTemplate)
elif sOrP[i] == 'P':
#print('parallel connection')
matrixTemplate = numpy.array([[1.0, 0.0], [0.0, 1.0]])
matrixTemplate[1][0] = 1 / frequenciesList[0][i]
globals()['matrix%s' % i] = matrixTemplate
#print(matrixTemplate)
I then need to multiply the created matrices together:
Ty = matrix0 @ matrix1 @ matrix2 @ matrix3 @ matrix4 @ matrix5 @ matrix6 @ matrix7 @ matrix8 @ matrix9
This works but the code has to be able to take multiple inputs with potentially more or fewer matrices being created. In that case it wouldn't work.
Would it be possible to do the multiplication part using a loop or function?
You could use a list (or a dictionary) to hold your matrices:
matrices = []
for i in range(len(node2)):
if (sOrP[i] == 'S'):
#print('series connection')
matrixTemplate = numpy.array([[1.0, 0.0],[0.0, 1.0]]) #Got to put 1.0 else it doesnt work
matrixTemplate[0][1] = frequenciesList[0][i]
matrices.append(matrixTemplate)
#print(matrixTemplate)
elif (sOrP[i] == 'P'):
#print('parallel connection')
matrixTemplate = numpy.array([[1.0, 0.0],[0.0, 1.0]])
matrixTemplate[1][0] = 1/frequenciesList[0][i]
matrices.append(matrixTemplate)
#print(matrixTemplate)
And then use reduce
and numpy.matmul
to compute your total matrix product:
from functools import reduce
Ty = reduce(numpy.matmul, matrices)
You can use either a loop or a numpy function.
Loop implementation:
matrixes = [M1, M2, ..., Mn]
A = matrixes[0]
for i in range(1, len(matrixes)):
B = matrixes[i]
A = np.dot(A, B)
First iteration: A = M1, B = M2; M1.M2
Second iteration: A = M1.M2, B = M3; M1.M2.M3
...
Numpy function: numpy.linalg.multi_dot(matrixes)
Setting the variables you have done is a pretty terrible way if doing it, as you seem to realize already. If your matrices are all nice and square, you only need one variable to hold the entire stack, shaped (len(node2), 2, 2)
.
Another point is your indexing. Numpy arrays are not lists. Your indices should look like [1, 0]
, not [1][0]
. Answers like the following shameless plug explain why: https://stackoverflow.com/a/60919478/2988730 .
Let's assume that sOrP
and frequenciesList
are numpy arrays. If they aren't, wrap them in a call to np.array
. You can make the stack like this:
matrices = np.broadcast_to([[[1, 0], [0, 1]]], (len(node2), 2, 2)).copy()
maskS = (sOrP == 'S')
maskP = (sOrP == 'P')
matrices[maskS, 0, 1] = frequenciesList[maskS]
matrices[maskP, 1, 0] = 1 / frequenciesList[maskP]
You can verify that matrices[i]
is equivalent to matrixi
in your original construction.
The simple way to multiply all the matrices together would be using a loop:
Ty = np.eye(2)
for mat in matrices:
Ty @= mat
But numpy is all about vectorization. As it happens, np.linalg.multidot
was made to optimize this exact operation:
Ty = np.linalg.multidot(matrices)
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.