Truss - Linear truss 3D element with analytical integration (pyfe3d.truss)#
Note
The BeamC element is recommended because of the better
physical representation.
Note
The Truss element does not support linear buckling
analysis.
Defines the two-node element Truss, with six degrees-of-freedom
per node, its probe TrussProbe and TrussData, which
gives the number of sparse entries per element of each structural matrix.
The cross-section and material properties are given by a
BeamProp object.
- class pyfe3d.truss.Truss#
Truss 3D element for axial- and torsion-only behavior
Nodal connectivity for the truss element:
______ --> u ->>- rx 1 2
Note
The
BeamCis recommended because of the better physical representation.The constructor stores
pinprobe, setseid,pid,n1,n2,c1andc2to-1, and sets theinit_k_*positions,lengthand the rotation matrix to0. The methods use the attributes updated by the others:update_rotation_matrix()readsc1andc2;update_probe_xe()reads the rotation matrix and updateslength;update_KC0(),update_M()andupdate_probe_finte()readlengthand the rotation matrix;update_probe_finte()also readsprobe.ue, updated byupdate_probe_ue().- Parameters:
- p
TrussProbeobject Probe of the element, stored in
probe. It can be shared with other elements.
- p
- Attributes:
- eid,int
Element identification number.
- pid,int
Property identification number.
- length,double
Element length, dimension length. Updated by
update_length().- r11, r12, r13, r21, r22, r23, r31, r32, r33double
Entries \(T_{ij}\) of the transformation matrix \(\boldsymbol{T}_{3\times 3}\) from element to global coordinates, whose columns are the element axes. Dimensionless.
- c1, c2int
Position of each node in the global stiffness matrix, i.e. of the first of its
6degrees-of-freedom. The coordinates of the node are read from the positionc1//2orc2//2of the array of nodal coordinates.- n1, n2int
Node identification number.
- init_k_KC0, init_k_Mint
Position in the arrays storing the sparse data for the structural matrices, where the entries of this element start, see
TrussDatafor their number.- probe,
TrussProbeobject Pointer to the probe.
Methods
update_KC0(self, long[, long[, double[, ...)Update sparse vectors for linear constitutive stiffness matrix KC0
update_M(self, long[, long[, double[, ...)Update sparse vectors for mass matrix M
update_fint(self, double[, BeamProp prop)Update the internal force vector
update_length(self)Update element length
update_probe_finte(self, BeamProp prop)Update the internal force vector of the probe
update_probe_ue(self, double[)Update the local displacement vector of the probe of the element
update_probe_xe(self, double[)Update the 3D coordinates of the probe of the element
update_rotation_matrix(self, double[)Update the rotation matrix of the element
Notes
The strain energy of the element is
\[U = \frac{1}{2} \int_0^L \left( E A u_{,x}^2 + G J {r_x}_{,x}^2 \right) dx\]where \(E A\) and \(G J\) are the entries
C[0, 0]andC[3, 3]of the sectional stiffness matrixCofBeamProp, i.e.E*Aand the torsional stiffnessGJwhenCis not set; the other entries ofC, e.g. the extension-twist couplingC[0, 3], are not used. The axial displacement \(u\) and the twist rotation \(r_x\) are interpolated linearly between the nodes, in the element coordinate system, and \(L\) =length. The transverse translations \(v\), \(w\) and the rotations \(r_y\), \(r_z\) have no stiffness and must be supported by other elements or by boundary conditions; the element has no geometric stiffness matrix. The matrices and the internal forces are computed in element coordinates and transformed to global coordinates with the transformation matrix of the element, \(\boldsymbol{K} = \boldsymbol{T} \boldsymbol{K}_e \boldsymbol{T}^\top\), where \(\boldsymbol{T}\) is block diagonal with four copies of the matrix \(\boldsymbol{T}_{3\times 3}\) of the entries \(T_{ij}\) stored inr11, ..., r33, whose columns are the element axes.- c1#
c1: ‘int’
- c2#
c2: ‘int’
- eid#
eid: ‘int’
- init_k_KC0#
init_k_KC0: ‘int’
- init_k_M#
init_k_M: ‘int’
- length#
length: ‘double’
- n1#
n1: ‘int’
- n2#
n2: ‘int’
- pid#
pid: ‘int’
- probe#
probe: pyfe3d.truss.TrussProbe
- r11#
r11: ‘double’
- r12#
r12: ‘double’
- r13#
r13: ‘double’
- r21#
r21: ‘double’
- r22#
r22: ‘double’
- r23#
r23: ‘double’
- r31#
r31: ‘double’
- r32#
r32: ‘double’
- r33#
r33: ‘double’
- update_KC0(self, long[: :1] KC0r, long[: :1] KC0c, double[: :1] KC0v, BeamProp prop, int update_KC0v_only=0) void#
Update sparse vectors for linear constitutive stiffness matrix KC0
The 72 entries of the matrix of the element, in global coordinates, are written at the positions
init_k_KC0toinit_k_KC0 + 71: the row and column indices, built fromc1andc2, are stored inKC0randKC0c, and the values are added to those already inKC0v. The matrix is computed fromlength, the rotation matrix andC[0, 0]andC[3, 3]of the sectional stiffness matrix ofprop, see the notes ofTruss.lengthand the rotation matrix must be updated before, seeupdate_rotation_matrix()andupdate_probe_xe().- Parameters:
- KC0rnp.array
Array to store row positions of sparse values. 1-D array of integers of the C type
long, of size at leastinit_k_KC0 + 72.- KC0cnp.array
Array to store column positions of sparse values. Same type and size as
KC0r.- KC0vnp.array
Array to store sparse values. 1-D array of floats of size at least
init_k_KC0 + 72.- prop
BeamPropobject Beam property object from where the stiffness and mass attributes are read from.
- update_KC0v_onlyint, optional
The default
0means that the row and column indicesKC0randKC0cshould also be updated. Any other value will only update the stiffness matrix valuesKC0v.
Notes
In element coordinates,
KC0is the Hessian of the strain energy given in the notes ofTruss, with the entries \(\pm E A/L\) between the axial translations and \(\pm G J/L\) between the twist rotations of the two nodes.
- update_M(self, long[: :1] Mr, long[: :1] Mc, double[: :1] Mv, BeamProp prop, int mtype=0) void#
Update sparse vectors for mass matrix M
For the
Trusselement, the inertial termsintrho,intrhoy,intrhoz,intrhoy2andintrhoz2of the beam property are important.The entries of the matrix of the element, in global coordinates, are written from the position
init_k_M: 144 entries withmtype=0and 36 entries withmtype=1. The row and column indices, built fromc1andc2, are stored inMrandMc, and the values are added to those already inMv. The matrix is computed fromlength, the rotation matrix and the inertial terms above.lengthand the rotation matrix must be updated before, seeupdate_rotation_matrix()andupdate_probe_xe().- Parameters:
- Mrnp.array
Array to store row positions of sparse values. 1-D array of integers of the C type
long, of size at leastinit_k_M + 144(init_k_M + 36withmtype=1).- Mcnp.array
Array to store column positions of sparse values. Same type and size as
Mr.- Mvnp.array
Array to store sparse values. 1-D array of floats, of the same size as
Mr.- prop
BeamPropobject Beam property object from where the inertial attributes are read.
- mtypeint, optional
0 for consistent mass matrix, 1 for lumped mass matrix. Default
0. The element has no reduced-integration mass matrix,2.
- Raises:
- ValueError
If
mtypeis not 0 or 1.
Notes
The mass matrices come from the kinetic energy of the rigid cross section, whose point \((y, z)\) has the displacements \(u_x = u\), \(u_y = v - z r_x\) and \(u_z = w + y r_x\), with the three translations and the twist rotation \(r_x\) interpolated linearly:
\[T = \frac{1}{2} \int_0^L \Big[ m (\dot{u}^2 + \dot{v}^2 + \dot{w}^2) - 2 m_z \dot{v} \dot{r}_x + 2 m_y \dot{w} \dot{r}_x + (m_{yy} + m_{zz}) \dot{r}_x^2 \Big] dx\]with \(m\) =
intrho, \(m_y\) =intrhoy, \(m_z\) =intrhoz, \(m_{yy}\) =intrhoy2and \(m_{zz}\) =intrhoz2. The coupling terms, \(-m_z\) between \(v\) and \(r_x\) and \(+m_y\) between \(w\) and \(r_x\), are those ofBeamLR.update_M()andBeamC.update_M(). The rotations \(r_y\) and \(r_z\) have no inertia.mtype=0gives the consistent mass matrix, the Hessian of \(T\) with respect to the nodal velocities, integrated exactly along the element.mtype=1gives the lumped mass matrix, diagonal in element coordinates: at each node \(L m/2\) for the three translations and \(L (m_{yy} + m_{zz})/2\) for \(r_x\), without the coupling terms of \(m_y\) and \(m_z\).The lumped mass matrix follows the lumped mass matrix by Lobatto integration of Brockman (1987) [1], p. 2348, adapted to the beam: the two-point Gauss-Lobatto quadrature of \(T\), whose points are the nodes, gives a diagonal matrix only without the first moments of the density, which are therefore dropped. The consistent mass matrix is the integral of Petyt (2010) [2], Sec. 3.3, Eqs. (3.58) and (3.59), for each linearly interpolated field, e.g. \(L m/6\) times \([2, 1; 1, 2]\) for each translation, and Sec. 3.4, Eq. (3.102), with \(m_{yy} + m_{zz}\) in place of \(\rho I_x\), for the twist \(r_x\).
References
[1]Brockman, R. A., 1987, “Dynamics of the Bilinear Mindlin Plate Element,” Int. J. Numer. Methods Eng., 24(12), pp. 2343–2356. https://onlinelibrary.wiley.com/doi/pdf/10.1002/nme.1620241208
[2]Petyt, M., 2010, Introduction to Finite Element Vibration Analysis, 2nd ed., Cambridge University Press, Cambridge. https://doi.org/10.1017/CBO9780511761195
- update_fint(self, double[: :1] fint, BeamProp prop) void#
Update the internal force vector
Calls
update_probe_finte(prop), transforms the forces and moments ofprobe.finteto global coordinates with the rotation matrix and adds them tofintat the positionsc1toc1 + 5andc2toc2 + 5. The displacementsprobe.uemust be updated before, seeupdate_probe_ue().- Parameters:
- fintnp.array
Array that is updated in place with the internal forces. The internal forces stored in
fintare calculated in global coordinates. Methodupdate_probe_finte()is called to update the parameterfinteof theTrussProbewith the internal forces in local coordinates. 1-D array of size6*M, for \(M\) nodes in the model.- prop
BeamPropobject Beam property object from where the stiffness and mass attributes are read from.
- update_length(self) void#
Update element length
The distance between the two nodes, computed from the coordinates
probe.xein the element coordinate system, is stored in the attributelength. Called byupdate_probe_xe().
- update_probe_finte(self, BeamProp prop) void#
Update the internal force vector of the probe
The attribute
finteis updated with theTrussProbethe internal forces in local coordinates. While using this function, mind that the probe can be shared amongst more than one finite element, depending how you defined them, meaning that the probe will always safe the values from the last udpate.Note
The
finteattribute of objectTrussProbeis updated, accessible using.probe.finte.The 12 values of
finteare overwritten. They are computed fromlength, fromC[0, 0]andC[3, 3]of the sectional stiffness matrix ofprop, see the notes ofTruss, and from the displacementsprobe.ue, which must be updated before, seeupdate_probe_xe()andupdate_probe_ue(). Only the axial forces and the torsion moments are not zero.- Parameters:
- prop
BeamPropobject Beam property object from where the stiffness and mass attributes are read from.
- prop
- update_probe_ue(self, double[: :1] u) void#
Update the local displacement vector of the probe of the element
Note
The
ueattribute of objectTrussProbeis updated, accessible using.probe.ue.The translations and rotations of the two nodes, read from
uat the positionsc1toc1 + 5andc2toc2 + 5, are transformed to the element coordinate system with the transpose \(\boldsymbol{T}_{3\times 3}^\top\) of the transformation matrix, which must be updated before, seeupdate_rotation_matrix().- Parameters:
- uarray-like
Array with global displacements, for a total of \(M\) nodes in the model, this array will be arranged as: \(u_1, v_1, w_1, {r_x}_1, {r_y}_1, {r_z}_1, u_2, v_2, w_2, {r_x}_2, {r_y}_2, {r_z}_2, ..., u_M, v_M, w_M, {r_x}_M, {r_y}_M, {r_z}_M\). Translations of dimension length and rotations, 1-D array of size
6*M.
- update_probe_xe(self, double[: :1] x) void#
Update the 3D coordinates of the probe of the element
Note
The
xeattribute of objectTrussProbeis updated, accessible using.probe.xe.The coordinates of the two nodes, read from
xat the positionsc1//2andc2//2, are transformed to the element coordinate system with the transpose \(\boldsymbol{T}_{3\times 3}^\top\) of the transformation matrix, which must be updated before, seeupdate_rotation_matrix(). Thenupdate_length()is called, updatinglength.- Parameters:
- xarray-like
Array with global nodal coordinates, for a total of \(M\) nodes in the model, this array will be arranged as: \(x_1, y_1, z_1, x_2, y_2, z_2, ..., x_M, y_M, z_M\). Dimension length, 1-D array of size
3*M.
- update_rotation_matrix(self, double[: :1] x) void#
Update the rotation matrix of the element
Attributes
r11,r12,r13,r21,r22,r23,r31,r32,r33are updated, with the entries \(T_{ij}\) of the transformation matrix \(\boldsymbol{T}_{3\times 3}\) from element to global coordinates, whose columns are the element axes.The element coordinate system is determined, identifying the \(ijk\) components of each axis: \({x_e}_i, {x_e}_j, {x_e}_k\); \({y_e}_i, {y_e}_j, {y_e}_k\); \({z_e}_i, {z_e}_j, {z_e}_k\).
The element \(x\) axis goes from node 1 to node 2, whose coordinates are read from
xat the positionsc1//2andc2//2. The \(z\) axis is normal to the \(x\) axis and to the vector obtained by a cyclic permutation of the components of the \(x\) axis,(xj, xk, xi), the \(y\) axis completes the right-handed system, and the three axes are normalized.- Parameters:
- xarray-like
Array with global nodal coordinates, for a total of \(M\) nodes in the model, this array will be arranged as: \(x_1, y_1, z_1, x_2, y_2, z_2, ..., x_M, y_M, z_M\). Dimension length, 1-D array of size
3*M.
- class pyfe3d.truss.TrussData#
Used to allocate memory for the sparse matrices.
Each attribute is the number of entries that one
Trusselement writes in the arrays of rows, columns and values of a sparse matrix, at the consecutive positions that start at itsinit_k_KC0orinit_k_M. The constructor takes no argument and sets the values below.- Attributes:
KC0_SPARSE_SIZEintKC0_SPARSE_SIZE: ‘int’
M_SPARSE_SIZEintM_SPARSE_SIZE: ‘int’
- KC0_SPARSE_SIZE#
KC0_SPARSE_SIZE: ‘int’
- M_SPARSE_SIZE#
M_SPARSE_SIZE: ‘int’
- class pyfe3d.truss.TrussProbe#
Probe used for local coordinates, local displacements, local stresses etc
The idea behind using a probe is to avoid allocating larger memory buffers per finite element. The memory buffers are allocated per probe, and one probe can be shared amongst many finite elements, with the information being updated and retrieved on demand.
Note
The probe can be shared amongst more than one finite element, depending on how you defined them. Mind that the probe will always safe the values from the last udpate.
The constructor takes no argument and allocates the arrays below, filled with zeros.
- Attributes:
xearray-likexe: ‘double[::1]’
uearray-likeue: ‘double[::1]’
- finte,array-like
Array of size
NUM_NODES*DOF=12containing the element internal forces corresponding to the degrees-of-freedom described byue, forces and moments. Updated byTruss.update_probe_finte().
- finte#
finte: ‘double[::1]’
- ue#
ue: ‘double[::1]’
- xe#
xe: ‘double[::1]’