Example: More bars

This example is from Calfem manual (exs4.py).

Purpose:

Analysis of a plane truss.

Description:

Consider a plane truss, loaded by a single force P = 0.5 MN at 30 \(^\circ\) from normal.

more bars

The corresponding finite element model consists of ten elements and twelve degrees of freedom.

more bars2

First, import necessart modules.

[1]:
import numpy as np
import calfem.core as cfc

The topology is defined by the matrix

[2]:
Edof = np.array([
    [1, 2, 5, 6],
    [3, 4, 7, 8],
    [5, 6, 9, 10],
    [7, 8, 11, 12],
    [7, 8, 5, 6],
    [11, 12, 9, 10],
    [3, 4, 5, 6],
    [7, 8, 9, 10],
    [1, 2, 7, 8],
    [5, 6, 11, 12]
])

A global stiffness matrix K and a load vector f are defined. The load P is divided into x and y components and inserted in the load vector f.

[3]:
K = np.zeros([12,12])
f = np.zeros([12,1])

The element matrices Ke are computed by the function bar2e. These matrices are then assembled in the global stiffness matrix using the function assem.

[4]:
A = 25.0e-4
E = 2.1e11
ep = [E,A]

Element coordinates are defined as follows.

[5]:
ex = np.array([
    [0., 2.],
    [0., 2.],
    [2., 4.],
    [2., 4.],
    [2., 2.],
    [4., 4.],
    [0., 2.],
    [2., 4.],
    [0., 2.],
    [2., 4.]
])

ey = np.array([
    [2., 2.],
    [0., 0.],
    [2., 2.],
    [0., 0.],
    [0., 2.],
    [0., 2.],
    [0., 2.],
    [0., 2.],
    [2., 0.],
    [2., 0.]
])

All the element matrices are computed and assembled in the loop.

[6]:
for elx, ely, eltopo in zip(ex, ey, Edof):
    Ke = cfc.bar2e(elx, ely, ep)
    cfc.assem(eltopo, K, Ke)

The displacements in a and the support forces in r are computed by solving the system of equations considering the boundary conditions in bc.

[7]:
bc = np.array([1,2,3,4])

f[10]=0.5e6*np.sin(np.pi/6)
f[11]=-0.5e6*np.cos(np.pi/6)

a, r = cfc.solveq(K,f,bc)
[8]:
print("Displacement: ")
print(a)
Displacement:
[[ 0.        ]
 [ 0.        ]
 [ 0.        ]
 [ 0.        ]
 [ 0.00238453]
 [-0.0044633 ]
 [-0.00161181]
 [-0.00419874]
 [ 0.00303458]
 [-0.01068377]
 [-0.00165894]
 [-0.01133382]]
[9]:
print("Support force: ")
print(r)
Support force:
[[-8.66025404e+05]
 [ 2.40086918e+05]
 [ 6.16025404e+05]
 [ 1.92925784e+05]
 [ 4.65661287e-10]
 [-2.91038305e-11]
 [ 1.16415322e-10]
 [ 1.16415322e-10]
 [-4.65661287e-10]
 [ 3.49245965e-10]
 [-2.03726813e-10]
 [ 4.65661287e-10]]

The displacement at the point of loading is \(−1.7 · 10^{−3} m\) in the x-direction and \(−11.3 · 10^{−3} ~m\) in the y-direction. At the upper support the horizontal force is \(−0.866~MN\) and the vertical \(0.240 ~MN\). At the lower support the forces are \(0.616~MN\) and \(0.193~MN\), respectively. Normal forces are evaluated from element displacements. These are obtained from the global displacements a using the function extract. The normal forces are evaluated using the function bar2s.

[10]:
ed = cfc.extractEldisp(Edof,a)

N = np.zeros([Edof.shape[0]])

print("Element forces:")

i = 0
for elx, ely, eld in zip(ex, ey, ed):
    N[i] = cfc.bar2s(elx, ely, ep, eld)
    print("N%d = %g" % (i+1,N[i]))
    i+=1
Element forces:
N1 = 625938
N2 = -423100
N3 = 170640
N4 = -12372.8
N5 = -69447
N6 = 170640
N7 = -272838
N8 = -241321
N9 = 339534
N10 = 371051

The largest normal force N = 0.626 MN is obtained in element 1 and is equivalent to a normal stress σ = 250 MPa.

To reduce the quantity of input data, the element coordinates matrices Ex and Ey can alternatively be created from a global coordinate matrix Coord and a global topology matrix Dof using the function coordxtr, i.e.

[12]:
Coord = np.array([
[0, 2],
[0, 0],
[2, 2],
[2, 0],
[4, 2],
[4, 0]
])
[14]:
Dof = np.array([
[1, 2],
[3, 4],
[5, 6],
[7, 8],
[9, 10],
[11, 12]
])
[17]:
ex, ey = cfc.coordxtr(Edof, Coord, Dof)
[18]:
print(ex)
[18]:
array([[0., 2.],
       [0., 2.],
       [2., 4.],
       [2., 4.],
       [2., 2.],
       [4., 4.],
       [0., 2.],
       [2., 4.],
       [0., 2.],
       [2., 4.]])
[19]:
print(ey)
[19]:
array([[2., 2.],
       [0., 0.],
       [2., 2.],
       [0., 0.],
       [0., 2.],
       [0., 2.],
       [0., 2.],
       [0., 2.],
       [2., 0.],
       [2., 0.]])

As can be seen above, ex and ey is same as previous.