用对角线覆盖构建Scipy矩阵 [英] build Scipy matrix with diagonal overlays
问题描述
我想在偏移位置上覆盖几个大小为4x4的数组,以创建一个大数组,将重叠的元素添加到一起.
I would like to overlay several arrays of equal 4x4 size at offset positions creating a large array where the overlapping elements are added together.
[a] 0 0 0
0 [a+b] 0 0
0 0 [b+c] 0
0 0 0 [c+...
这是为了创建用于连续梁分析的刚度矩阵.这很容易用循环创建,但是使用Scipy稀疏矩阵例程有更好的方法吗? block_diag已关闭,但未提供叠加方法.
This is for the creation of a stiffness matrix for continuous beam analysis. This is easy enough to create with a loop, but is there a better way using Scipy sparse matrix routines? block_diag is close but does not provide a method for overlays.
Members = [[100.0, 1000.0],[100.0, 2000.0],[200.0, 2000.0]]
SSM = np.zeros((2*M+2,2*M+2), dtype = float)
i=0
for mem in Members:
a = SMX(mem)
print a
print "*"*40
SSM[i:i+4,i:i+4] = SSM[i:i+4,i:i+4] + a
print SSM
i +=2
def SMX(member):
""" Prismatic beam member stiffness function
Purpose: Create a member stiffness matrix for a given set of member parameters.
Input: Modulus of elasticity - E
Moment of inertia with respect to the z axis - Iz
Length of the span - L
Returns: 4 x 4 matrix representing the member stiffness with respect to end conditions
"""
L = member[0]
Iz = member[1]
pbms = np.zeros((4,4), dtype = float)
pbms[0,0] = (12.0 * E * Iz)/L**2
pbms[0,1] = (6.0 * E * Iz)/L**2
pbms[0,2] = -pbms[0,0]
pbms[0,3] = pbms[0,1]
pbms[1,0] = pbms[0,1]
pbms[1,1] = (4.0 * E * Iz)/L
pbms[1,2] = -pbms[0,1]
pbms[1,3] = (2.0 * E * Iz)/L
pbms[2,0] = pbms[0,2]
pbms[2,1] = -pbms[0,1]
pbms[2,2] = pbms[0,0]
pbms[2,3] = -pbms[0,1]
pbms[3,0] = pbms[0,1]
pbms[3,1] = pbms[1,3]
pbms[3,2] = -pbms[0,1]
pbms[3,3] = pbms[1,1]
return pbms
结果输出:
[[ 12000. 6000. -12000. 6000.]
[ 6000. 400000. -6000. 200000.]
[ -12000. -6000. 12000. -6000.]
[ 6000. 200000. -6000. 400000.]]
****************************************
[[ 12000. 6000. -12000. 6000. 0. 0. 0. 0.]
[ 6000. 400000. -6000. 200000. 0. 0. 0. 0.]
[ -12000. -6000. 12000. -6000. 0. 0. 0. 0.]
[ 6000. 200000. -6000. 400000. 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. 0. 0. 0.]
[ 0. 0. 0. 0. 0. 0. 0. 0.]]
[[ 24000. 12000. -24000. 12000.]
[ 12000. 800000. -12000. 400000.]
[ -24000. -12000. 24000. -12000.]
[ 12000. 400000. -12000. 800000.]]
****************************************
[[ 12000. 6000. -12000. 6000. 0. 0. 0.
0.]
[ 6000. 400000. -6000. 200000. 0. 0. 0.
0.]
[ -12000. -6000. 36000. 6000. -24000. 12000. 0.
0.]
[ 6000. 200000. 6000. 1200000. -12000. 400000. 0.
0.]
[ 0. 0. -24000. -12000. 24000. -12000. 0.
0.]
[ 0. 0. 12000. 400000. -12000. 800000. 0.
0.]
[ 0. 0. 0. 0. 0. 0. 0.
0.]
[ 0. 0. 0. 0. 0. 0. 0.
0.]]
[[ 6000. 3000. -6000. 3000.]
[ 3000. 400000. -3000. 200000.]
[ -6000. -3000. 6000. -3000.]
[ 3000. 200000. -3000. 400000.]]
****************************************
[[ 12000. 6000. -12000. 6000. 0. 0. 0.
0.]
[ 6000. 400000. -6000. 200000. 0. 0. 0.
0.]
[ -12000. -6000. 36000. 6000. -24000. 12000. 0.
0.]
[ 6000. 200000. 6000. 1200000. -12000. 400000. 0.
0.]
[ 0. 0. -24000. -12000. 30000. -9000. -6000.
3000.]
[ 0. 0. 12000. 400000. -9000. 1200000. -3000.
200000.]
[ 0. 0. 0. 0. -6000. -3000. 6000.
-3000.]
[ 0. 0. 0. 0. 3000. 200000. -3000.
400000.]]
只是注意到我忽略了上面的M = 3.
Just noticed that I left out M = 3 above.
推荐答案
I don't see the problem with scipy.sparse.block_diag
, but I probably don't understand exactly what you mean by "overlay". For example, the output you illustrated in the question can be formed like this:
In [41]: from scipy import sparse
In [42]: a = np.array([[1, 2], [3, 4]])
In [43]: b = np.array([[5, 6], [7, 8]])
In [44]: c = np.array([[9, 10], [11, 12]])
In [45]: m = sparse.block_diag([a, a+b, b+c])
In [46]: m.A
Out[46]:
array([[ 1, 2, 0, 0, 0, 0],
[ 3, 4, 0, 0, 0, 0],
[ 0, 0, 6, 8, 0, 0],
[ 0, 0, 10, 12, 0, 0],
[ 0, 0, 0, 0, 14, 16],
[ 0, 0, 0, 0, 18, 20]])
编辑:浏览了有关光束分析的一些材料之后,我认为我对您如何覆盖矩阵的方法有了更好的了解.
Edit: After browsing through some material on beam analysis, I think I understand better how you want to overlay the matrices.
例如,假设有四个2x2数组a,b,c和d.以下是叠加层"的示例:
For example, suppose there are four 2x2 arrays a, b, c, and d. An example of an "overlay" is the following:
a[0,0] a[0,1] 0 0 0
a[1,0] a[1,1]+b[0,0] b[0,1] 0 0
0 b[1,0] b[1,1]+c[0,0] c[0,1] 0
0 0 c[1,0] c[1,1]+d[0,0] d[0,1]
0 0 0 d[1,0] d[1,1]
此处演示了一种使用block_diag
形成这种情况的方法.它包含一个表达式,每个2x2数组都有一个术语,可以将其重写为循环,因此它并不能真正回答您的问题.
One way to form this with block_diag
is demonstrated here. It involves an expression with a term for each 2x2 array, which could be rewritten as a loop, so it doesn't really answer your question.
In [92]: a,b,c,d
Out[92]:
(array([[1, 2],
[3, 4]]),
array([[5, 6],
[7, 8]]),
array([[ 9, 10],
[11, 12]]),
array([[13, 14],
[15, 16]]))
In [93]: bd = sparse.block_diag # A convenient alias
In [94]: m = bd([a,0,0,0])+bd([0,b,0,0])+bd([0,0,c,0])+bd([0,0,0,d])
In [95]: m.A
Out[95]:
array([[ 1, 2, 0, 0, 0],
[ 3, 9, 6, 0, 0],
[ 0, 7, 17, 10, 0],
[ 0, 0, 11, 25, 14],
[ 0, 0, 0, 15, 16]])
这篇关于用对角线覆盖构建Scipy矩阵的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!