Math#
Warning
Shear terms are not doubled for strain-like tensors, instead all math operations take care of the reduced vector storage.
Symmetric properties of dyadic products
The minor and major-symmetric property indicates whether the fourth-order tensor as a result of a dyadic product of two symmetric second-order tensors may be transferred into a reduced matrix storage. Special cases of minor but not major-symmetry and vice versa exist but are not shown here.
Function |
\(\boldsymbol{A} \ne \boldsymbol{B}\) |
\(\boldsymbol{A} = \boldsymbol{B}\) |
---|---|---|
❌ |
✔️ |
|
✔️ |
✔️ |
|
❌ |
❌ |
|
❌ |
❌ |
- hyperelastic.math.astensor(A, mode=2)[source]#
Convert a three-dimensional tensor from symmetric (Voigt-notation) vector/matrix storage into full array-storage.
- Parameters:
A (np.ndarray) – A three-dimensional second- or fourth-order tensor in reduced symmetric (Voigt) vector/matrix storage.
mode (int, optional) – The mode, 2 for second-order and 4 for fourth-order tensors (default is 2).
- Returns:
A three-dimensional second- or fourth-order tensor in full array-storage.
- Return type:
np.ndarray
Notes
This is the inverse operation of
asvoigt()
.For a symmetric 3x3 second-order tensor \(C_{ij} = C_{ji}\), the entries are re-created from a 6x1 vector.
(1)#\[\begin{split}\boldsymbol{C} = \begin{bmatrix} C_{11} & C_{22} & C_{33} & C_{12} & C_{23} & C_{13} \end{bmatrix}^T \longrightarrow % \boldsymbol{C} = \begin{bmatrix} C_{11} & C_{12} & C_{13} \\ C_{12} & C_{22} & C_{23} \\ C_{13} & C_{23} & C_{33} \end{bmatrix} \qquad\end{split}\]For a (at least minor) symmetric 3x3x3x3 fourth-order tensor \(A_{ijkl} = A_{jikl} = A_{ijlk} = A_{jilk}\), the entries are re-created from a 6x6 matrix.
(2)#\[ \begin{align}\begin{aligned}\begin{split}\mathbb{A} = \begin{bmatrix} A_{1111} & A_{1122} & A_{1133} & A_{1112} & A_{1123} & A_{1113} \\ A_{2211} & A_{2222} & A_{2233} & A_{2212} & A_{2223} & A_{2213} \\ \dots & \dots & \dots & \dots & \dots & \dots \\ A_{1311} & A_{1322} & A_{1333} & A_{1312} & A_{1323} & A_{1313} \end{bmatrix}\end{split}\\\begin{split}\longrightarrow \begin{bmatrix} A_{1111} & A_{1112} & A_{1113} & A_{1121} & A_{1122} & A_{1123} & A_{1131} & A_{1132} & A_{1133} \\ % A_{1211} & A_{1212} & A_{1213} & A_{1221} & A_{1222} & A_{1223} & A_{1231} & A_{1232} & A_{1233} \\ % \dots & \dots & \dots & \dots & \dots & \dots & \dots & \dots & \dots \\ A_{3111} & A_{3112} & A_{3113} & A_{3121} & A_{3122} & A_{3123} & A_{3131} & A_{3132} & A_{3133} % \end{bmatrix} \qquad\end{split}\end{aligned}\end{align} \]Examples
>>> from hyperelastic.math import asvoigt, astensor >>> import numpy as np
>>> C = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> C6 = asvoigt(C, mode=2) >>> D = astensor(C6, mode=2) >>> np.allclose(C, D) True
>>> D array([[1. , 1.3, 1.5], [1.3, 1.1, 1.4], [1.5, 1.4, 1.2]])
>>> A = np.einsum("ij,kl", C, C) >>> A66 = asvoigt(A, mode=4) >>> B = astensor(A66, mode=4) >>> np.allclose(A, B) True
- hyperelastic.math.asvoigt(A, mode=2)[source]#
Convert a three-dimensional tensor from full array-storage into reduced symmetric (Voigt-notation) vector/matrix storage.
- Parameters:
A (np.ndarray) – A three-dimensional second- or fourth-order tensor in full array-storage.
mode (int, optional) – The mode, 2 for second-order and 4 for fourth-order tensors (default is 2).
- Returns:
A three-dimensional second- or fourth-order tensor in reduced symmetric (Voigt) vector/matrix storage.
- Return type:
np.ndarray
Notes
This is the inverse operation of
astensor()
.For a symmetric 3x3 second-order tensor \(C_{ij} = C_{ji}\), the upper triangle entries are inserted into a 6x1 vector, starting from the main diagonal, followed by the consecutive next upper diagonals.
(3)#\[\begin{split}\boldsymbol{C} = \begin{bmatrix} C_{11} & C_{12} & C_{13} \\ C_{12} & C_{22} & C_{23} \\ C_{13} & C_{23} & C_{33} \end{bmatrix} \qquad \longrightarrow \boldsymbol{C} = \begin{bmatrix} C_{11} & C_{22} & C_{33} & C_{12} & C_{23} & C_{13} \end{bmatrix}^T\end{split}\]For a (at least minor) symmetric 3x3x3x3 fourth-order tensor \(A_{ijkl} = A_{jikl} = A_{ijlk} = A_{jilk}\), rearranged to 9x9, the upper triangle entries are inserted into a 6x6 matrix, starting from the main diagonal, followed by the consecutive next upper diagonals.
(4)#\[ \begin{align}\begin{aligned}\begin{split}\begin{bmatrix} A_{1111} & A_{1112} & A_{1113} & A_{1121} & A_{1122} & A_{1123} & A_{1131} & A_{1132} & A_{1133} \\ % A_{1211} & A_{1212} & A_{1213} & A_{1221} & A_{1222} & A_{1223} & A_{1231} & A_{1232} & A_{1233} \\ % \dots & \dots & \dots & \dots & \dots & \dots & \dots & \dots & \dots \\ A_{3111} & A_{3112} & A_{3113} & A_{3121} & A_{3122} & A_{3123} & A_{3131} & A_{3132} & A_{3133} % \end{bmatrix} \qquad\end{split}\\\begin{split}\longrightarrow \mathbb{A} = \begin{bmatrix} A_{1111} & A_{1122} & A_{1133} & A_{1112} & A_{1123} & A_{1113} \\ A_{2211} & A_{2222} & A_{2233} & A_{2212} & A_{2223} & A_{2213} \\ \dots & \dots & \dots & \dots & \dots & \dots \\ A_{1311} & A_{1322} & A_{1333} & A_{1312} & A_{1323} & A_{1313} \end{bmatrix}\end{split}\end{aligned}\end{align} \]Examples
>>> from hyperelastic.math import asvoigt >>> import numpy as np
>>> C = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> asvoigt(C, mode=2) array([1. , 1.1, 1.2, 1.3, 1.4, 1.5])
>>> A = np.einsum("ij,kl", C, C) >>> asvoigt(A, mode=4) array([[1. , 1.1 , 1.2 , 1.3 , 1.4 , 1.5 ], [1.1 , 1.21, 1.32, 1.43, 1.54, 1.65], [1.2 , 1.32, 1.44, 1.56, 1.68, 1.8 ], [1.3 , 1.43, 1.56, 1.69, 1.82, 1.95], [1.4 , 1.54, 1.68, 1.82, 1.96, 2.1 ], [1.5 , 1.65, 1.8 , 1.95, 2.1 , 2.25]])
- hyperelastic.math.cdya(A, B, out=None)[source]#
The full-symmetric crossed-dyadic product of two symmetric second-order tensors in reduced vector storage.
- Parameters:
A (np.ndarray) – First symmetric second-order tensor in reduced vector storage.
B (np.ndarray) – Second symmetric second-order tensor in reduced vector storage.
out (np.ndarray or None, optional) – A location into which the result is stored. If provided, it must have a shape that the inputs broadcast to. If not provided or None, a freshly-allocated array is returned (default is None).
- Returns:
Symmetric crossed-dyadic product in reduced matrix storage.
- Return type:
np.ndarray
Notes
The result of the symmetric crossed-dyadic product of two symmetric second order tensors is a minor- and major-symmetric fourth-order tensor.
(5)#\[ \begin{align}\begin{aligned}\mathbb{C} &= \frac{1}{2} \left( \boldsymbol{A} \odot \boldsymbol{B} + \boldsymbol{B} \odot \boldsymbol{A} \right)\\\mathbb{C} &= \frac{1}{4} \left( \boldsymbol{A} \overline{\otimes} \boldsymbol{B} + \boldsymbol{A} \underline{\otimes} \boldsymbol{B} + \boldsymbol{B} \overline{\otimes} \boldsymbol{A} + \boldsymbol{B} \underline{\otimes} \boldsymbol{A} \right)\\\mathbb{C}_{ijkl} &= \frac{1}{4} \left( A_{ik}~B_{jl} + A_{il}~B_{kj} + B_{ik}~A_{jl} + B_{il}~A_{kj} \right)\end{aligned}\end{align} \]Note
The technical implementation is based on an answer of Jérôme Richard (see stackoverflow).
Examples
>>> from hyperelastic.math import asvoigt, astensor, cdya >>> import numpy as np
>>> C = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> D = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2])[::-1].reshape(3, 3)
>>> CD = (np.einsum("ik,jl", C, D) + np.einsum("il,kj", C, D)) / 2 >>> DC = (np.einsum("ik,jl", D, C) + np.einsum("il,kj", D, C)) / 2
>>> A = (CD + DC) / 2
>>> C6 = asvoigt(C, mode=2) >>> D6 = asvoigt(D, mode=2) >>> cdya(C6, D6) array([[1.2 , 1.82 , 2.25 , 1.48 , 2.025 , 1.65 ], [1.82 , 1.21 , 1.82 , 1.485 , 1.485 , 1.825 ], [2.25 , 1.82 , 1.2 , 2.025 , 1.48 , 1.65 ], [1.48 , 1.485 , 2.025 , 1.515 , 1.7375, 1.7575], [2.025 , 1.485 , 1.48 , 1.7375, 1.515 , 1.7575], [1.65 , 1.825 , 1.65 , 1.7575, 1.7575, 1.735 ]])
>>> np.allclose(A, astensor(cdya(C6, D6), mode=4)) True
>>> np.allclose(A, astensor(cdya(D6, C6), mode=4)) True
- hyperelastic.math.cdya_ik(A, B, out=None)[source]#
The overlined-dyadic product of two symmetric second-order tensors in reduced vector storage, where the inner indices (the second index of the first tensor and the first index of the second tensor) are interchanged.
- Parameters:
A (np.ndarray) – First symmetric second-order tensor in reduced vector storage.
B (np.ndarray) – Second symmetric second-order tensor in reduced vector storage.
out (np.ndarray or None, optional) – A location into which the result is stored. If provided, it must have a shape that the inputs broadcast to. If not provided or None, a freshly-allocated array is returned (default is None).
- Returns:
Overlined-dyadic product in full-array storage.
- Return type:
np.ndarray
Notes
The result of the overlined-dyadic product of two symmetric second order tensors is a major- (but not minor-) symmetric fourth-order tensor. This is also the case for \(\boldsymbol{A} = \boldsymbol{B}\).
(6)#\[ \begin{align}\begin{aligned}\mathbb{C} &= \boldsymbol{A} \overline{\otimes} \boldsymbol{B}\\\mathbb{C}_{ijkl} &= A_{ik}~B_{jl}\end{aligned}\end{align} \]Examples
>>> from hyperelastic.math import asvoigt, cdya_ik >>> import numpy as np
>>> C = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> D = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2])[::-1].reshape(3, 3)
>>> A = np.einsum("ik,jl", C, D)
>>> C6 = asvoigt(C, mode=2) >>> D6 = asvoigt(D, mode=2)
>>> np.allclose(A, cdya_ik(C6, D6)) True
- hyperelastic.math.cdya_il(A, B, out=None)[source]#
The underlined-dyadic product of two symmetric second-order tensors in reduced vector storage, where the right indices of the two tensors are interchanged.
- Parameters:
A (np.ndarray) – First symmetric second-order tensor in reduced vector storage.
B (np.ndarray) – Second symmetric second-order tensor in reduced vector storage.
out (np.ndarray or None, optional) – A location into which the result is stored. If provided, it must have a shape that the inputs broadcast to. If not provided or None, a freshly-allocated array is returned (default is None).
- Returns:
Underlined-dyadic product in full-array storage.
- Return type:
np.ndarray
Notes
The result of the underlined-dyadic product of two symmetric second order tensors is a non-symmetric fourth-order tensor. In case of \(\boldsymbol{A} = \boldsymbol{B}\), the fourth-order tensor is major-symmetric.
(7)#\[ \begin{align}\begin{aligned}\mathbb{C} &= \boldsymbol{A} \underline{\otimes} \boldsymbol{B}\\\mathbb{C}_{ijkl} &= A_{il}~B_{kj}\end{aligned}\end{align} \]Examples
>>> from hyperelastic.math import asvoigt, cdya_il >>> import numpy as np
>>> C = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> D = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2])[::-1].reshape(3, 3)
>>> A = np.einsum("il,kj", C, D)
>>> C6 = asvoigt(C, mode=2) >>> D6 = asvoigt(D, mode=2)
>>> np.allclose(A, cdya_il(C6, D6)) True
- hyperelastic.math.ddot(A, B, mode=(2, 2))[source]#
The double-dot product of two symmetric tensors in reduced vector storage, where the two innermost indices of both tensors are contracted.
- Parameters:
A (np.ndarray) – First symmetric second- or fourth-order tensor in reduced vector storage.
B (np.ndarray) – Second symmetric second- or fourth-order tensor in reduced vector storage.
mode (2-tuple, optional) – The mode, 2 for second-order and 4 for fourth-order tensors (default is (2, 2)).
- Returns:
Double-dot product of two symmetric tensors in scalar or reduced vector/matrix storage.
- Return type:
np.ndarray
Notes
(8)#\[ \begin{align}\begin{aligned}C &= \boldsymbol{A} : \boldsymbol{B}\\C &= A_{ij} : B_{ij}\end{aligned}\end{align} \](9)#\[ \begin{align}\begin{aligned}\boldsymbol{C} &= \boldsymbol{A} : \mathbb{B}\\C_{kl} &= A_{ij} : \mathbb{B}_{ijkl}\end{aligned}\end{align} \](10)#\[ \begin{align}\begin{aligned}\boldsymbol{C} &= \mathbb{B} : \boldsymbol{A}\\C_{ij} &= \mathbb{B}_{ijkl} : A_{kl}\end{aligned}\end{align} \](11)#\[ \begin{align}\begin{aligned}\mathbb{C} &= \mathbb{A} : \mathbb{B}\\\mathbb{C}_{ijmn} &= \mathbb{A}_{ijkl} : \mathbb{A}_{klmn}\end{aligned}\end{align} \]Examples
>>> from hyperelastic.math import asvoigt, ddot >>> import numpy as np
>>> A = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> B = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2])[::-1].reshape(3, 3)
>>> A4 = np.einsum("ij,kl", A, B) >>> B4 = (np.einsum("ik,jl", A, A) + np.einsum("il,kj", A, A)) / 2
>>> ddot(asvoigt(A), asvoigt(B), mode=(2, 2)) 15.39
>>> ddot(asvoigt(A), asvoigt(B4, mode=4), mode=(2, 4)) array([18.899, 18.863, 21.698, 18.903, 20.253, 20.316])
>>> ddot(asvoigt(B4, mode=4), asvoigt(A), mode=(4, 2)) array([18.899, 18.863, 21.698, 18.903, 20.253, 20.316])
>>> ddot(asvoigt(A4, mode=4), asvoigt(B4, mode=4), mode=(4, 4)) array([[18.519 , 18.787 , 21.944 , 18.675 , 20.326 , 20.225 ], [20.3709, 20.6657, 24.1384, 20.5425, 22.3586, 22.2475], [22.2228, 22.5444, 26.3328, 22.41 , 24.3912, 24.27 ], [24.0747, 24.4231, 28.5272, 24.2775, 26.4238, 26.2925], [25.9266, 26.3018, 30.7216, 26.145 , 28.4564, 28.315 ], [27.7785, 28.1805, 32.916 , 28.0125, 30.489 , 30.3375]])
- hyperelastic.math.det(A)[source]#
The determinant of a symmetric second-order tensor in reduced vector storage.
- Parameters:
A (np.ndarray) – Symmetric second-order tensor in reduced vector storage.
- Returns:
Determinant of a symmetric second-order tensor in reduced vector storage.
- Return type:
np.ndarray
Examples
>>> from hyperelastic.math import asvoigt, det >>> import numpy as np
>>> A = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> B = asvoigt(A)
>>> det(B) 0.3169999999999993
>>> np.allclose(det(B), np.linalg.det(A)) True
- hyperelastic.math.dev(A)[source]#
The deviatoric part of a three-dimensional second-order tensor.
- Parameters:
A (np.ndarray) – Symmetric second-order tensor in reduced vector storage.
- Returns:
Deviatoric part of the symmetric second-order tensor in reduced vector storage.
- Return type:
np.ndarray
Notes
(12)#\[\text{dev}(\boldsymbol{C}) = \boldsymbol{C} - \frac{\text{tr}(\boldsymbol{C})}{3} \boldsymbol{I}\]
- hyperelastic.math.dot(A, B, mode=(2, 2))[source]#
The dot product of two symmetric second-order tensors in reduced vector storage, where the second index of the first tensor and the first index of the second tensor are contracted.
- Parameters:
A (np.ndarray) – First symmetric second-order tensor in reduced vector storage.
B (np.ndarray) – Second symmetric second-order tensor in reduced vector storage.
mode (2-tuple, optional) – The mode, 2 for second-order and 4 for fourth-order tensors (default is (2, 2)).
- Returns:
Dot product of two symmetric second-order tensors in reduced vector storage.
- Return type:
np.ndarray
Notes
(13)#\[ \begin{align}\begin{aligned}C &= \boldsymbol{A} ~ \boldsymbol{B}\\C_{ij} &= A_{ik} B_{kj}\end{aligned}\end{align} \]Examples
>>> from hyperelastic.math import asvoigt, dot >>> import numpy as np
>>> A = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> B = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2])[::-1].reshape(3, 3)
>>> C = dot(asvoigt(A), asvoigt(B), mode=(2, 2)) >>> C array([[5.27, 4.78, 4.69], [5.2 , 4.85, 4.78], [5.56, 5.2 , 5.27]])
>>> D = A @ B >>> np.allclose(C, D) True
- hyperelastic.math.dya(A, B, out=None)[source]#
The dyadic product of two symmetric second-order tensors in reduced vector storage.
- Parameters:
A (np.ndarray) – First symmetric second-order tensor in reduced vector storage.
B (np.ndarray) – Second symmetric second-order tensor in reduced vector storage.
out (np.ndarray or None, optional) – A location into which the result is stored. If provided, it must have a shape that the inputs broadcast to. If not provided or None, a freshly-allocated array is returned (default is None).
- Returns:
Dyadic product in reduced matrix storage.
- Return type:
np.ndarray
Notes
The result of the dyadic product of two symmetric second order tensors is a minor- (but not major-) symmetric fourth-order tensor. For the case of \(\boldsymbol{A} = \boldsymbol{B}\), the result is both major- and minor- symmetric.
(14)#\[ \begin{align}\begin{aligned}\mathbb{C} &= \boldsymbol{A} \otimes \boldsymbol{B}\\\mathbb{C}_{ijkl} &= A_{ij}~B_{kl}\end{aligned}\end{align} \]Examples
>>> from hyperelastic.math import asvoigt, astensor, dya >>> import numpy as np
>>> C = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> D = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2])[::-1].reshape(3, 3)
>>> A = np.einsum("ij,kl", C, D)
>>> C6 = asvoigt(C, mode=2) >>> D6 = asvoigt(D, mode=2)
>>> np.allclose(A, astensor(dya(C6, D6), mode=4)) True
- hyperelastic.math.eye(A=None)[source]#
A 3x3 tensor in Voigt-storage with ones on the diagonal and zeros elsewhere. The dimension is taken from the input argument (a symmetric second-order tensor in reduced vector storage).
- Parameters:
A (np.ndarray or None, optional) – Symmetric second- or fourth-order tensor in reduced vector storage (default is None).
- Returns:
Identity matrix in reduced vector storage.
- Return type:
np.ndarray
Notes
(15)#\[\boldsymbol{I} = \begin{bmatrix} 1 & 1 & 1 & 0 & 0 & 0 \end{bmatrix}^T\]Examples
>>> from hyperelastic.math import asvoigt, eye >>> import numpy as np
>>> A = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> B = asvoigt(A) >>> eye(B) array([1., 1., 1., 0., 0., 0.])
- hyperelastic.math.inv(A, determinant=None, out=None)[source]#
The inverse of a symmetric second-order tensor in reduced vector storage.
- Parameters:
A (np.ndarray) – Symmetric second-order tensor in reduced vector storage.
determinant (np.ndarray or None, optional) – The determinant of the symmetric second-order tensor (default is None).
out (np.ndarray or None, optional) – A location into which the result is stored. If provided, it must have a shape that the inputs broadcast to. If not provided or None, a freshly-allocated array is returned (default is None).
- Returns:
Inverse of a symmetric second-order tensor in reduced vector storage.
- Return type:
np.ndarray
Notes
(16)#\[\boldsymbol{C} \boldsymbol{C}^{-1} = \boldsymbol{I}\]Examples
>>> from hyperelastic.math import asvoigt, inv >>> import numpy as np
>>> A = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> B = asvoigt(A)
>>> inv(B) array([-2.01892744, -3.31230284, -1.86119874, 1.70347003, 1.73501577, 0.5362776 ])
>>> np.allclose(dot(B, inv(B)), np.eye(3)) True
- hyperelastic.math.trace(A)[source]#
The trace of a symmetric second-order tensor in reduced vector storage as the sum of the main diagonal.
- Parameters:
A (np.ndarray) – Symmetric second-order tensor in reduced vector storage.
- Returns:
Trace of a symmetric second-order tensor in reduced vector storage.
- Return type:
np.ndarray
Notes
(17)#\[ \begin{align}\begin{aligned}\text{tr}\left(\boldsymbol{C}\right) &= \boldsymbol{C} : \boldsymbol{I} = C_{11} + C_{22} + C_{33}\\C_{kk} &= C_{ij} : \delta_{ij}\end{aligned}\end{align} \]Examples
>>> from hyperelastic.math import asvoigt, trace >>> import numpy as np
>>> A = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3)
>>> trA = trace(asvoigt(A)) >>> trA 3.3
>>> np.allclose(trA, np.trace(A)) True
- hyperelastic.math.transpose(A)[source]#
The major-transpose of a symmetric fourth-order tensor in reduced vector storage.
- Parameters:
A (np.ndarray) – Symmetric fourth-order tensor in reduced vector storage.
- Returns:
Major-transpose of a symmetric fourth-order tensor in reduced vector storage.
- Return type:
np.ndarray
Notes
(18)#\[\mathbb{A}_{ijkl}^T = \mathbb{A}_{klij}\]Examples
>>> from hyperelastic.math import asvoigt, dya, transpose >>> import numpy as np
>>> A = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2]).reshape(3, 3) >>> B = np.array([1.0, 1.3, 1.5, 1.3, 1.1, 1.4, 1.5, 1.4, 1.2])[::-1].reshape(3, 3)
>>> C = dya(asvoigt(A), asvoigt(B)) >>> C array([[1.2 , 1.1 , 1. , 1.4 , 1.3 , 1.5 ], [1.32, 1.21, 1.1 , 1.54, 1.43, 1.65], [1.44, 1.32, 1.2 , 1.68, 1.56, 1.8 ], [1.56, 1.43, 1.3 , 1.82, 1.69, 1.95], [1.68, 1.54, 1.4 , 1.96, 1.82, 2.1 ], [1.8 , 1.65, 1.5 , 2.1 , 1.95, 2.25]])
>>> transpose(C) array([[1.2 , 1.32, 1.44, 1.56, 1.68, 1.8 ], [1.1 , 1.21, 1.32, 1.43, 1.54, 1.65], [1. , 1.1 , 1.2 , 1.3 , 1.4 , 1.5 ], [1.4 , 1.54, 1.68, 1.82, 1.96, 2.1 ], [1.3 , 1.43, 1.56, 1.69, 1.82, 1.95], [1.5 , 1.65, 1.8 , 1.95, 2.1 , 2.25]])
>>> D = astensor(C, mode=4) >>> E = astensor(transpose(C), mode=4) >>> np.allclose(D, np.einsum("klij", E)) True