Homog1#

Conduct homogenization using an example outlined in ‘Computational Homogenization of Heterogeneous Materials with Finite Elements’.

Reference: https://doi.org/10.1007/978-3-030-18383-7 Section 4.7 with corrected values on page 89 (Erratum).

  • RVE
  • Periodic boundary conditions
  • E [MPa]
  • v
  • $ux$
  • $uy$
  • $\sigma_{xx}$
  • $\sigma_{yy}$
  • $\sigma_{xy}$
f = 0.4
c1111 = 6.743336039055451
c1122 = 4.5944253955082095
c1212 = 0.6256584299841418

 16 import matplotlib.pyplot as plt
 17 import numpy as np
 18
 19 from EasyFEA import Display, Models, ElemType, Simulations
 20 from EasyFEA.Geoms import Points, Circle
 21 from EasyFEA.FEM import LagrangeCondition, FeArray
 22 from typing import Optional
 23
 24
 25 def Compute_ukl(
 26     simu: Simulations.Elastic,
 27     nodes_kubc: np.ndarray,
 28     Ekl: np.ndarray,
 29     paired_nodes: Optional[np.ndarray] = None,
 30     pltSol=False,
 31     useMean0=False,
 32 ):
 33     simu.Bc_Init()
 34     mesh = simu.mesh
 35     coord = mesh.coord
 36
 37     usePBC = paired_nodes is not None
 38
 39     def func_ux(x, y, z):
 40         return Ekl.dot([x, y])[0]
 41
 42     def func_uy(x, y, z):
 43         return Ekl.dot([x, y])[1]
 44
 45     directions = ["x", "y"]
 46     simu.add_dirichlet(nodes_kubc, [func_ux, func_uy], directions)
 47
 48     if usePBC:
 49         for n0, n1 in paired_nodes:
 50             nodes = np.array([n0, n1])
 51
 52             for d, direction in enumerate(directions):
 53                 dofs = simu.Bc_dofs_nodes(nodes, [direction])
 54
 55                 values = Ekl @ [
 56                     coord[n0, 0] - coord[n1, 0],
 57                     coord[n0, 1] - coord[n1, 1],
 58                 ]
 59                 value = values[d]
 60
 61                 condition = LagrangeCondition(
 62                     "elastic", nodes, dofs, [direction], [value], [1, -1]
 63                 )
 64                 simu._Bc_Add_Lagrange(condition)
 65
 66     if useMean0:
 67         nodes = mesh.nodes
 68         vect = np.ones(mesh.Nn) * 1 / mesh.Nn
 69
 70         # sum u_i / Nn = 0
 71         dofs = simu.Bc_dofs_nodes(nodes, ["x"])
 72         condition = LagrangeCondition("elastic", nodes, dofs, ["x"], [0], [vect])
 73         simu._Bc_Add_Lagrange(condition)
 74
 75         # sum v_i / Nn = 0
 76         dofs = simu.Bc_dofs_nodes(nodes, ["y"])
 77         condition = LagrangeCondition("elastic", nodes, dofs, ["y"], [0], [vect])
 78         simu._Bc_Add_Lagrange(condition)
 79
 80     ukl = simu.Solve()
 81
 82     simu.Save_Iter()
 83
 84     if pltSol:
 85         Display.Plot_Result(simu, "ux", deformFactor=0.3)
 86         Display.Plot_Result(simu, "uy", deformFactor=0.3)
 87
 88         Display.Plot_Result(simu, "Sxx", deformFactor=0.3)
 89         Display.Plot_Result(simu, "Syy", deformFactor=0.3)
 90         Display.Plot_Result(simu, "Sxy", deformFactor=0.3)
 91
 92     return ukl
 93
 94
 95 if __name__ == "__main__":
 96     Display.Clear()
 97
 98     # ----------------------------------------------
 99     # Configuration
100     # ----------------------------------------------
101
102     # use Periodic boundary conditions ?
103     usePBC = True
104
105     # ----------------------------------------------
106     # Mesh
107     # ----------------------------------------------
108     meshSize = 1 / 15
109
110     p0 = (-1 / 2, -1 / 2)
111     p1 = (1 / 2, -1 / 2)
112     p2 = (1 / 2, 1 / 2)
113     p3 = (-1 / 2, 1 / 2)
114     pts = [p0, p1, p2, p3]
115     contour = Points(pts, meshSize)
116
117     # inclusion
118     f = 0.4
119     r = 1 * np.sqrt(f / np.pi)
120     inclusion = Circle((0, 0), 2 * r, meshSize, isHollow=False)
121
122     mesh = contour.Mesh_2D([inclusion], ElemType.TRI6)
123
124     Display.Plot_Mesh(mesh, title="RVE")
125
126     if usePBC:
127         nodes_kubc = mesh.Nodes_Tags(["P0", "P1", "P2", "P3"])
128         paired_nodes = mesh.Get_Paired_Nodes(nodes_kubc, True)
129     else:
130         nodes_kubc = mesh.Nodes_Tags(["L0", "L1", "L2", "L3"])
131         paired_nodes = None
132
133     # ----------------------------------------------
134     # Material and Simulation
135     # ----------------------------------------------
136     elements_inclusion = mesh.Elements_Tags(["S1"])
137     elements_matrix = mesh.Elements_Tags(["S0"])
138
139     E = np.zeros_like(mesh.groupElem.elements, dtype=float)
140     v = np.zeros_like(mesh.groupElem.elements, dtype=float)
141
142     E[elements_matrix] = 1  # MPa
143     v[elements_matrix] = 0.45
144
145     if elements_inclusion.size > 0:
146         E[elements_inclusion] = 50
147         v[elements_inclusion] = 0.3
148
149     material = Models.Elastic.Isotropic(2, E, v, planeStress=False)
150
151     simu = Simulations.Elastic(mesh, material)
152
153     Display.Plot_Result(simu, E, nodeValues=False, title="E [MPa]")
154     Display.Plot_Result(simu, v, nodeValues=False, title="v")
155
156     # ----------------------------------------------
157     # Homogenization
158     # ----------------------------------------------
159     r2 = np.sqrt(2)
160     E11 = np.array([[1, 0], [0, 0]])
161     E22 = np.array([[0, 0], [0, 1]])
162     E12 = np.array([[0, 1 / r2], [1 / r2, 0]])
163
164     u11 = Compute_ukl(simu, nodes_kubc, E11, paired_nodes)
165     u22 = Compute_ukl(simu, nodes_kubc, E22, paired_nodes)
166     u12 = Compute_ukl(simu, nodes_kubc, E12, paired_nodes, True)
167
168     u11_e = mesh.Locates_sol_e(u11, asFeArray=True)
169     u22_e = mesh.Locates_sol_e(u22, asFeArray=True)
170     u12_e = mesh.Locates_sol_e(u12, asFeArray=True)
171
172     # ----------------------------------------------
173     # Effective elasticity tensor (C_hom)
174     # ----------------------------------------------
175     U_e = FeArray.zeros(*u11_e.shape, 3)
176
177     U_e[..., 0] = u11_e
178     U_e[..., 1] = u22_e
179     U_e[..., 2] = u12_e
180
181     matrixType = "mass"
182     wJ_e_pg = mesh.Get_weightedJacobian_e_pg(matrixType)
183     B_e_pg = mesh.Get_B_e_pg(matrixType)
184
185     C_Mat = Models.Reshape_variable(material.C, *B_e_pg.shape[:2])
186
187     # Be careful here you have to use all the area even if there are holes
188     # if you use the mesh area, multiply C_hom by the porosity (1-f)
189     C_hom = (wJ_e_pg * C_Mat @ B_e_pg @ U_e).sum((0, 1)) / mesh.area
190
191     if inclusion.isHollow and mesh.area != 1:
192         C_hom *= 1 - f
193
194     # Display.Plot_BoundaryConditions(simu)
195
196     print(f"f = {f}")
197     print(f"c1111 = {C_hom[0, 0]}")
198     print(f"c1122 = {C_hom[0, 1]}")
199     print(f"c1212 = {C_hom[2, 2] / 2}")
200
201     plt.show()

Total running time of the script: (0 minutes 1.108 seconds)

Gallery generated by Sphinx-Gallery