Beispiel #1
0
    def __init__(self,
                 material=None,
                 fes=None,
                 integration_rule=None,
                 material_csys=CSys(),
                 assoc_geom=None):
        """Constructor.

        :param material: Material object.
        :param fes: Finite element set object.
        :param integration_rule: Integration rule object.
        """
        super().__init__(fes=fes,
                         integration_rule=integration_rule,
                         material_csys=material_csys,
                         assoc_geom=assoc_geom)
        self.material = material
        self._phis = None
        e = getattr(self.material, 'e', None)
        if e is not None:
            e = self.material.e
            if self.material.nu < 0.3:
                nu = self.material.nu
            else:
                nu = 0.3 + (self.material.nu - 0.3) / 2.0
        else:
            e1 = getattr(self.material, 'e1', None)
            if e1 is not None:
                e = min(self.material.e1, self.material.e2, self.material.e3)
                nu = min(self.material.nu12, self.material.nu13,
                         self.material.nu23)
            else:
                raise Exception(
                    'No clues on how to construct the stabilization material')
        self.stabilization_material = MatDeforTriaxLinearIso(e=e, nu=nu)
        # Now try to figure out which Poisson ratio to use in the optimal scaling
        # factor(to account for geometry)
        nu = getattr(self.material, "nu", None)
        if nu is not None:
            self.nu = self.material.nu
        else:
            nu12 = getattr(self.material, "nu12", None)
            if nu12 is not None:
                self.nu = max(self.material.nu12, self.material.nu13,
                              self.material.nu23)
            else:
                raise Exception(
                    'No clues on how to construct the stabilization material')
Beispiel #2
0
from scipy.sparse.csgraph import reverse_cuthill_mckee
import spyfe.bipwr
import time
from spyfe.meshing.exporters.vtkexporter import vtkexport

start0 = time.time()
E = 200e9
nu = 0.3
rho = 8000
a = 10.0
b = a
h = 0.05

htol = h / 1000
na, nb, nh = 6,6,4
m = MatDeforTriaxLinearIso(rho=rho, e=E, nu=nu)

start = time.time()
fens, fes = h8_block(a, b, h, na, nb, nh)
fens, fes = h8_to_h20(fens, fes)
print('Mesh generation', time.time() - start)
geom = NodalField(fens=fens)
u = NodalField(nfens=fens.count(), dim=3)
cn = fenode_select(fens, box=numpy.array([0, 0, 0, b, 0, h]), inflate=htol)
for j in cn:
    u.set_ebc([j], comp=0, val=0.0)
    u.set_ebc([j], comp=1, val=0.0)
    u.set_ebc([j], comp=2, val=0.0)
u.apply_ebc()
femmk = FEMMDeforLinear(material=m, fes=fes, integration_rule=GaussRule(dim=3, order=2))
femmk.associate_geometry(geom)
import time

start0 = time.time()
E = 1000
nu = 0.4999
W = 2.5
H = 5
L = 50
# nW, nL, nH = 20, 20, 20
nW, nL, nH = 4, 20, 4
htol = min(L, H, W) / 1000
magn = -0.2 * 12.2334 / 4
Force = magn * W * H * 2
Force * L**3 / (3 * E * W * H**3 * 2 / 12)
uzex = -12.0935378981478
m = MatDeforTriaxLinearIso(e=E, nu=nu)

start = time.time()
fens, fes = t4_block(W, L, H, nW, nL, nH, orientation='ca')
fens, fes = t4_to_t10(fens, fes)
print('Mesh generation', time.time() - start)

model_data = {}
model_data['fens'] = fens
model_data['regions'] = [{'femm': FEMMDeforLinearQT10MS(material=m, fes=fes)}]

algo_common.plot_mesh(model_data)

model_data['boundary_conditions'] = {}
# Clamped face
cn = fenode_select(fens, box=numpy.array([0, W, 0, 0, 0, H]), inflate=htol)
Beispiel #4
0
class FEMMDeforLinearMS(FEMMDeforLinear):
    """
    Class for small-strain linear deformation based on the mean-strain
    technology with stabilization by full quadrature (energy-sampling stabilization).

    """
    def __init__(self,
                 material=None,
                 fes=None,
                 integration_rule=None,
                 material_csys=CSys(),
                 assoc_geom=None):
        """Constructor.

        :param material: Material object.
        :param fes: Finite element set object.
        :param integration_rule: Integration rule object.
        """
        super().__init__(fes=fes,
                         integration_rule=integration_rule,
                         material_csys=material_csys,
                         assoc_geom=assoc_geom)
        self.material = material
        self._phis = None
        e = getattr(self.material, 'e', None)
        if e is not None:
            e = self.material.e
            if self.material.nu < 0.3:
                nu = self.material.nu
            else:
                nu = 0.3 + (self.material.nu - 0.3) / 2.0
        else:
            e1 = getattr(self.material, 'e1', None)
            if e1 is not None:
                e = min(self.material.e1, self.material.e2, self.material.e3)
                nu = min(self.material.nu12, self.material.nu13,
                         self.material.nu23)
            else:
                raise Exception(
                    'No clues on how to construct the stabilization material')
        self.stabilization_material = MatDeforTriaxLinearIso(e=e, nu=nu)
        # Now try to figure out which Poisson ratio to use in the optimal scaling
        # factor(to account for geometry)
        nu = getattr(self.material, "nu", None)
        if nu is not None:
            self.nu = self.material.nu
        else:
            nu12 = getattr(self.material, "nu12", None)
            if nu12 is not None:
                self.nu = max(self.material.nu12, self.material.nu13,
                              self.material.nu23)
            else:
                raise Exception(
                    'No clues on how to construct the stabilization material')

    def associate_geometry(self, geom):
        """Associate geometry.

        This method needs to be called before any computation with the FEMM is performed.
        It calculates the stabilization factors dependent on the geometry.
        :param geom: Geometry field.
        :return: Nothing.  The object is modified.
        """
        raise Exception('Needs to be overridden')

    def stiffness(self, geom, u):
        fes = self.fes
        bfuns, gradbfunpars, npts, pc, w = self.integration_data()
        mcs = self.material_csys
        md = self.material.modulidata()  # material stiffness in material CS
        d = numpy.zeros_like(md)  # material stiffness in global CS
        dstab = numpy.zeros_like(d)
        transfd = numpy.zeros_like(d)
        self.material.stress_vector_rotation_matrix(transfd,
                                                    None)  #generate identity
        if mcs.isconstant and not mcs.isidentity:
            mcsmtx = mcs.eval_matrix()  # constant
            self.material.stress_vector_rotation_matrix(transfd, mcsmtx.T)
        d_constant = self.material.moduli_are_constant()
        if d_constant:
            self.material.tangent_moduli(md)
        self.stabilization_material.tangent_moduli(
            dstab
        )  # the stabilization material assumed to have constant moduli
        bmatfun, b = self.fes.bmatdata(self.fes.nfens)
        bbar = copy.copy(b)
        assm = SysmatAssemblerSparseFixedSymm(fes, u)
        gradbfun = list()
        jac = list()
        gradbfunmean = numpy.zeros((fes.nfens, geom.dim))
        for j in range(npts):
            gradbfun.append(numpy.zeros((fes.nfens, geom.dim)))
            jac.append(0.0)
        for i in range(fes.conn.shape[0]):
            x = geom.values[fes.conn[i, :], :]
            # Calculate mean basis function gradient + volume of the element
            vol = 0
            gradbfunmean.fill(0.0)
            for j in range(npts):
                jacmat = dot(x.T, gradbfunpars[j])
                jac[j] = fes.jac_volume(fes.conn[i, :], bfuns[j], jacmat, x)
                fes.gradbfun(gradbfun[j], gradbfunpars[j], jacmat)
                dvol = (jac[j] * w[j])
                gradbfunmean += gradbfun[j] * dvol
                vol = vol + dvol
            gradbfunmean /= vol
            bmatfun(bbar, None, gradbfunmean,
                    None)  # strain-displacement matrix in global CS
            if not d_constant:
                self.material.tangent_moduli(md)
            numpy.copyto(d, md)  # moduli in material CS
            if not mcs.isidentity:  # Transformation is required
                if not mcs.isconstant:  # Do I need to evaluate the local mat orient?
                    mcsmtx = mcs.eval_matrix(c, jacmat, fes.label[i])
                    self.material.stress_vector_rotation_matrix(
                        transfd, mcsmtx.T)
                self.material.rotate_stiffness(d,
                                               transfd)  # moduli in global CS
            # These matrices are in the global Cartesian coordinate system
            assm.elmtx[i, :, :] = dot(
                bbar.T, dot(vol * (d - self._phis[i] * dstab), bbar))
            for j in range(npts):
                bmatfun(b, None, gradbfun[j],
                        None)  # strain-displacement matrix in global CS
                assm.elmtx[i, :, :] += dot(
                    b.T, dot((self._phis[i] * jac[j] * w[j]) * dstab, b))
        return assm.make_matrix()

    def nz_ebc_loads(self, geom, u):
        fes = self.fes
        bfuns, gradbfunpars, npts, pc, w = self.integration_data()
        mcs = self.material_csys
        md = self.material.modulidata()  # material stiffness in material CS
        d = numpy.zeros_like(md)  # material stiffness in global CS
        dstab = numpy.zeros_like(d)
        transfd = numpy.zeros_like(d)
        self.material.stress_vector_rotation_matrix(transfd,
                                                    None)  # generate identity
        if mcs.isconstant and not mcs.isidentity:
            mcsmtx = mcs.eval_matrix()  # constant
            self.material.stress_vector_rotation_matrix(transfd, mcsmtx.T)
        d_constant = self.material.moduli_are_constant()
        if d_constant:
            self.material.tangent_moduli(md)
        self.stabilization_material.tangent_moduli(
            dstab
        )  # the stabilization material assumed to have constant moduli
        pu = numpy.zeros((self.fes.conn.shape[1] * u.dim, ),
                         dtype=numpy.float64)
        bmatfun, b = self.fes.bmatdata(self.fes.nfens)
        bbar = copy.copy(b)
        assm = SysvecAssembler(fes, u)
        gradbfun = list()
        jac = list()
        gradbfunmean = numpy.zeros((fes.nfens, geom.dim))
        for j in range(npts):
            gradbfun.append(numpy.zeros((fes.nfens, geom.dim)))
            jac.append(0.0)
        for i in range(fes.conn.shape[0]):
            x = geom.values[fes.conn[i, :], :]
            u.gather_fixed_values_vec(fes.conn[i, :], pu)
            if any(pu != 0.0):
                # Calculate mean basis function gradient + volume of the element
                vol = 0
                gradbfunmean.fill(0.0)
                for j in range(npts):
                    jacmat = dot(x.T, gradbfunpars[j])
                    jac[j] = fes.jac_volume(fes.conn[i, :], bfuns[j], jacmat,
                                            x)
                    fes.gradbfun(gradbfun[j], gradbfunpars[j], jacmat)
                    dvol = (jac[j] * w[j])
                    gradbfunmean += gradbfun[j] * dvol
                    vol = vol + dvol
                gradbfunmean /= vol
                bmatfun(bbar, None, gradbfunmean,
                        None)  # strain-displacement matrix in global CS
                if not d_constant:
                    self.material.tangent_moduli(md)
                numpy.copyto(d, md)  # moduli in material CS
                if not mcs.isidentity:  # Transformation is required
                    if not mcs.isconstant:  # Do I need to evaluate the local mat orient?
                        mcsmtx = mcs.eval_matrix(c, jacmat, fes.label[i])
                        self.material.stress_vector_rotation_matrix(
                            transfd, mcsmtx.T)
                    self.material.rotate_stiffness(
                        d, transfd)  # moduli in global CS
                # These matrices are in the global Cartesian coordinate system
                ke = dot(bbar.T, dot(vol * (d - self._phis[i] * dstab), bbar))
                for j in range(npts):
                    bmatfun(b, None, gradbfun[j],
                            None)  # strain-displacement matrix in global CS
                    ke += dot(b.T,
                              dot((self._phis[i] * jac[j] * w[j]) * dstab, b))
                assm.elvec[i, :] = dot(ke, pu).ravel()
        return assm.make_vector()

    def inspect_integration_points(self,
                                   fe_list,
                                   inspector,
                                   idat,
                                   geom,
                                   un1,
                                   un,
                                   dt=0.0,
                                   dtempn1=None,
                                   outcs=CSys(),
                                   output=OUTPUT_CAUCHY):
        """Inspect integration point quantities.

        :param fe_list: indexes of the finite elements that are to be inspected:
               The fes to be included are: fes.conn[fe_list, :].
        :param inspector: inspector function,
        :param idat: data for inspector function,
        :param geom: Geometry field.
        :param un1: Displacement field at the time t_n+1.
        :param un: Displacement field at time t_n.
        :param dt: Time step from t_n to t_n+1.
        :param dtempn1: Temperature increment field or None.
        :return: idat: data for inspector function
        """
        fes = self.fes
        bfuns, gradbfunpars, npts, pc, w = self.integration_data()
        mcs = self.material_csys
        if mcs.isconstant:
            mcsmtx = mcs.eval_matrix()  # constant
        if outcs is not None and outcs.isconstant:
            outcsmtx = outcs.eval_matrix()  # constant
        if dtempn1 is None:
            dtemps = numpy.zeros((geom.nfens, 1))
        else:
            dtemps = dtempn1.values
        bmatfun, bbar = self.fes.bmatdata(self.fes.nfens)
        elemu = numpy.zeros((fes.nfens * un1.dim, ))
        gradbfun = list()
        jac = list()
        gradbfunmean = numpy.zeros((fes.nfens, geom.dim))
        for j in range(npts):
            gradbfun.append(numpy.zeros((fes.nfens, geom.dim)))
            jac.append(0.0)
        quantityout = None
        vout = None
        for i in fe_list:
            x = geom.values[fes.conn[i, :], :]
            # Calculate mean basis function gradient + volume of the element
            vol = 0
            gradbfunmean.fill(0.0)
            for j in range(npts):
                jacmat = dot(x.T, gradbfunpars[j])
                jac[j] = fes.jac_volume(fes.conn[i, :], bfuns[j], jacmat, x)
                fes.gradbfun(gradbfun[j], gradbfunpars[j], jacmat)
                dvol = jac[j] * w[j]
                gradbfunmean += gradbfun[j] * dvol
                vol = vol + dvol
            gradbfunmean /= vol
            bmatfun(bbar, None, gradbfunmean, None)
            un1.gather_values_vec(fes.conn[i, :], elemu)
            c = dot(bfuns[j].T, x)  # Model location of the quadrature point
            u_c = dot(bfuns[j].T, un1.values[fes.conn[
                i, :], :])  # Displacement of the quad point
            strain = dot(bbar,
                         elemu)  # strain in global Cartesian coordinate system
            mstrain = numpy.copy(strain)  #strain in material coordinate
            # If necessary, transform the strain from the global CS to the material CS
            if not mcs.isidentity:  # Transformation is required
                if not mcs.isconstant:  # Do I need to evaluate the local mat orient?
                    mcsmtx = mcs.eval_matrix(c, jacmat, fes.label[i])
                self.material.rotate_strain_vector(mstrain, mcsmtx, strain)
            dtemp = dot(bfuns[j].T, dtemps[fes.conn[i, :]])
            quantityout = self.material.state(None,
                                              strain=strain,
                                              dtemp=dtemp,
                                              output=output,
                                              quantityout=quantityout)
            if output == OUTPUT_CAUCHY:  # vector quantity: transformation may be required
                if vout is None:
                    vout = numpy.zeros_like(quantityout)
                if not mcs.isidentity:  # Transformation is required
                    self.material.rotate_stress_vector(vout, mcsmtx.T,
                                                       quantityout)
                    quantityout[:] = vout[:]
                if not outcs.isidentity:  # Transformation is required
                    if not outcs.isconstant:  # Do I need to evaluate the local mat orient?
                        outcsmtx = outcs.eval_matrix(c, jacmat, fes.label[i])
                    self.material.rotate_stress_vector(vout, outcsmtx,
                                                       quantityout)
                    quantityout[:] = vout[:]
            else:  #
                pass
            if inspector is not None:
                inspector(idat, quantityout, c, u_c, pc[j, :])
        return idat
Beispiel #5
0
from scipy.sparse.csgraph import reverse_cuthill_mckee
import time
from spyfe.meshing.exporters.vtkexporter import vtkexport
from spyfe.meshing.importers import abaqus_importer
from spyfe.materials.mat_defor import OUTPUT_CAUCHY
import scipy.io

start0 = time.time()

# Reference value is the axial stress at point A (at the spherical part, plane of symmetry, interior)
sigma_z_A_ref = -105e6

E = 210e9
nu = 0.3
alpha = 2.3e-4
m = MatDeforTriaxLinearIso(e=E, nu=nu, alpha=alpha)

start = time.time()
fens, feslist = abaqus_importer.import_mesh('LE11_H20_90deg.inp')
# Account for the instance rotation
fens = rotate_mesh(fens, math.pi * 90. / 180 * numpy.array([1.0, 0.0, 0.0]),
                   numpy.array([0.0, 0.0, 0.0]))
for fes in feslist:
    print(fes.count())
fes = feslist[0]
scipy.io.savemat('LE11_H20_90deg.mat', {'xyz': fens.xyz, 'conn': fes.conn})
print('Mesh import', time.time() - start)

geom = NodalField(fens=fens)
u = NodalField(nfens=fens.count(), dim=3)
htol = 1.0 / 1000