コード例 #1
0
def test_calc_linear_buckling():
    E11 = 71.e9
    nu = 0.33
    plyt = 0.007
    lam = read_stack([0], plyt=plyt, laminaprop=(E11, E11, nu))
    ans = {
        'edge-based': 41.85273,
        'cell-based': 6.98852939,
        'cell-based-no-smoothing': 4.921956
    }
    for prop_from_nodes in [True, False]:
        for k0s_method in [
                'edge-based', 'cell-based', 'cell-based-no-smoothing'
        ]:
            mesh = read_mesh(
                os.path.join(THISDIR, 'nastran_plate_16_nodes.dat'))
            for tria in mesh.elements.values():
                tria.prop = lam
            for node in mesh.nodes.values():
                node.prop = lam
            k0 = calc_k0(mesh, prop_from_nodes)
            add_k0s(k0, mesh, prop_from_nodes, k0s_method, alpha=0.2)

            # running static subcase first
            dof = 5
            n = k0.shape[0] // 5
            fext = np.zeros(n * dof, dtype=np.float64)
            fext[mesh.nodes[4].index * dof + 0] = -500.
            fext[mesh.nodes[7].index * dof + 0] = -500.
            fext[mesh.nodes[5].index * dof + 0] = -1000.
            fext[mesh.nodes[6].index * dof + 0] = -1000.

            # boundary conditions
            def bc(K):
                for i in [1, 10, 11, 12]:
                    for j in [0, 1, 2]:
                        K[mesh.nodes[i].index * dof + j, :] = 0
                        K[:, mesh.nodes[i].index * dof + j] = 0

                for i in [2, 3, 4, 5, 6, 7, 8, 9]:
                    for j in [1, 2]:
                        K[mesh.nodes[i].index * dof + j, :] = 0
                        K[:, mesh.nodes[i].index * dof + j] = 0

            bc(k0)
            k0 = coo_matrix(k0)
            d = solve(k0, fext, silent=True)
            kG = calc_kG(d, mesh, prop_from_nodes)
            bc(kG)
            kG = coo_matrix(kG)

            eigvals, eigvecs = lb(k0, kG, silent=True)
            print('k0s_method, eigvals[0]', k0s_method, eigvals[0])

            assert np.isclose(eigvals[0], ans[k0s_method])
コード例 #2
0
def test_calc_linear_static():
    mesh = read_mesh(os.path.join(THISDIR, 'nastran_plate_16_nodes.dat'))
    E11 = 71.e9
    nu = 0.33
    plyt = 0.007
    lam = read_stack([0], plyt=plyt, laminaprop=(E11, E11, nu))
    for tria in mesh.elements.values():
        tria.prop = lam
    for node in mesh.nodes.values():
        node.prop = lam
    for prop_from_nodes in [False, True]:
        for k0s_method in ['cell-based', 'cell-based-no-smoothing']: #, 'edge-based'
            k0 = calc_k0(mesh, prop_from_nodes)
            add_k0s(k0, mesh, prop_from_nodes, k0s_method, alpha=0.2)

            k0run = k0.copy()

            dof = 5
            n = k0.shape[0] // dof
            fext = np.zeros(n*dof, dtype=np.float64)
            fext[mesh.nodes[4].index*dof + 2] = 500.
            fext[mesh.nodes[7].index*dof + 2] = 500.
            fext[mesh.nodes[5].index*dof + 2] = 1000.
            fext[mesh.nodes[6].index*dof + 2] = 1000.
            i, j = np.indices(k0run.shape)

            # boundary conditions
            for nid in [1, 10, 11, 12]:
                for j in [0, 1, 2, 3]:
                    k0run[mesh.nodes[nid].index*dof+j, :] = 0
                    k0run[:, mesh.nodes[nid].index*dof+j] = 0

            k0run = coo_matrix(k0run)
            u = solve(k0run, fext, silent=True)
            ans = np.loadtxt(os.path.join(THISDIR, 'nastran_plate_16_nodes.result.txt'),
                    dtype=float)
            xyz = np.array([n.xyz for n in mesh.nodes.values()])
            ind = np.lexsort((xyz[:, 1], xyz[:, 0]))
            xyz = xyz[ind]
            nodes = np.array(list(mesh.nodes.values()))[ind]
            pick = [n.index for n in nodes]
            assert np.allclose(u[2::5][pick].reshape(4, 4).T, ans, rtol=0.05)
コード例 #3
0
from scipy.sparse import coo_matrix
from composites.laminate import read_stack
from structsolve import solve, lb

from meshless.espim.read_mesh import read_mesh
from meshless.espim.plate2d_calc_k0 import calc_k0
from meshless.espim.plate2d_calc_kG import calc_kG
from meshless.espim.plate2d_add_k0s import add_k0s

THISDIR = os.path.dirname(inspect.getfile(inspect.currentframe()))

E11 = 71.e9
nu = 0.33
plyt = 0.007
laminaprop = (E11, E11, nu)
lam = read_stack([0], plyt=plyt, laminaprop=laminaprop, calc_scf=True)
prop_from_nodes = False
k0s_method = 'cell-based'
mesh = read_mesh(os.path.join(THISDIR, 'nastran_test.dat'))

nodes = mesh.nodes.values()
for tria in mesh.elements.values():
    tria.prop = lam
for node in nodes:
    node.prop = lam
k0 = calc_k0(mesh, prop_from_nodes)
add_k0s(k0, mesh, prop_from_nodes, k0s_method)

dof = 5
N = k0.shape[0] // 5
コード例 #4
0
def test_static_pressure(plot=False):
    # number of nodes
    nx = 29
    ny = 29

    # geometry
    a = 3
    b = 7

    # material properties
    E = 200e9
    nu = 0.3
    h = 0.005
    lam = read_stack(stack=[0], plyt=h, laminaprop=[E, E, nu])

    xtmp = np.linspace(0, a, nx)
    ytmp = np.linspace(0, b, ny)
    xmesh, ymesh = np.meshgrid(xtmp, ytmp)

    # getting nodes
    ncoords = np.vstack((xmesh.T.flatten(), ymesh.T.flatten())).T
    x = ncoords[:, 0]
    y = ncoords[:, 1]
    nids = 1 + np.arange(ncoords.shape[0])
    nid_pos = dict(zip(nids, np.arange(len(nids))))

    nids_mesh = nids.reshape(nx, ny)

    n1s = nids_mesh[:-1, :-1].flatten()
    n2s = nids_mesh[1:, :-1].flatten()
    n3s = nids_mesh[1:, 1:].flatten()
    n4s = nids_mesh[:-1, 1:].flatten()

    K = np.zeros((DOF * nx * ny, DOF * nx * ny))
    cyls = []
    for n1, n2, n3, n4 in zip(n1s, n2s, n3s, n4s):
        cyl = BFSCylinder()
        cyl.n1 = n1
        cyl.n2 = n2
        cyl.n3 = n3
        cyl.n4 = n4
        cyl.R = 1e100
        cyl.ABD = lam.ABD
        update_K(cyl, nid_pos, ncoords, K)
        cyls.append(cyl)

    # applying boundary conditions
    bk = np.zeros(K.shape[0], dtype=bool)

    # simply supported
    check = isclose(x, 0) | isclose(x, a) | isclose(y, 0) | isclose(y, b)
    bk[2::DOF] = check

    # eliminating all u,v displacements
    bk[0::DOF] = True
    bk[1::DOF] = True

    bu = ~bk  # same as np.logical_not, defining unknown DOFs

    # external force vector for point load at center
    f = np.zeros(K.shape[0])
    fmid = 1.

    # force at center node
    check = np.isclose(x, a / 2) & np.isclose(y, b / 2)
    f[2::DOF][check] = fmid
    assert f.sum() == fmid

    # sub-matrices corresponding to unknown DOFs
    Kuu = K[bu, :][:, bu]
    fu = f[bu]

    # solving
    Kuu = csc_matrix(Kuu)  # making Kuu a sparse matrix
    uu = spsolve(Kuu, fu)
    u = np.zeros(K.shape[0], dtype=float)
    u[bu] = uu

    w = u[2::DOF].reshape(nx, ny).T
    print('wmax', w.max())
    print('wmin', w.min())
    if plot:
        import matplotlib
        matplotlib.use('TkAgg')
        import matplotlib.pyplot as plt
        plt.gca().set_aspect('equal')
        levels = np.linspace(w.min(), w.max(), 300)
        plt.contourf(xmesh, ymesh, w, levels=levels)
        plt.colorbar()
        plt.show()
コード例 #5
0
def test_nat_freq(plot_mode=None):
    # number of nodes
    nx = 7  # along x
    ny = 7  # along y

    # geometry
    a = 0.6
    b = 0.2

    # material properties (Aluminum)
    E = 70e9
    nu = 0.3
    rho = 7.8e3
    h = 0.001
    lam = read_stack(stack=[0], plyt=h, laminaprop=[E, nu], rho=rho)

    # creating mesh
    x = np.linspace(0, a, nx)
    y = np.linspace(0, b, ny)
    xmesh, ymesh = np.meshgrid(x, y)

    # node coordinates and position in the global matrix
    ncoords = np.vstack((xmesh.T.flatten(), ymesh.T.flatten())).T
    nids = 1 + np.arange(ncoords.shape[0])
    nid_pos = dict(zip(nids, np.arange(len(nids))))

    nids_mesh = nids.reshape(nx, ny)

    n1s = nids_mesh[:-1, :-1].flatten()
    n2s = nids_mesh[1:, :-1].flatten()
    n3s = nids_mesh[1:, 1:].flatten()
    n4s = nids_mesh[:-1, 1:].flatten()

    K = np.zeros((DOF * nx * ny, DOF * nx * ny))
    M = np.zeros((DOF * nx * ny, DOF * nx * ny))
    cyls = []
    for n1, n2, n3, n4 in zip(n1s, n2s, n3s, n4s):
        cyl = BFSCylinder()
        cyl.n1 = n1
        cyl.n2 = n2
        cyl.n3 = n3
        cyl.n4 = n4
        cyl.ABD = lam.ABD
        cyl.h = h
        cyl.R = 1e100
        cyl.rho = lam.rho
        update_K(cyl, nid_pos, ncoords, K)
        update_M(cyl, nid_pos, M)
        cyls.append(cyl)

    # applying boundary conditions
    # simply supported

    # locating nodes
    bk = np.zeros(
        K.shape[0],
        dtype=bool)  # constrained DOFs, can be used to prescribe displacements

    x = ncoords[:, 0]
    y = ncoords[:, 1]

    # constraining w at all edges
    check = (np.isclose(x, 0.) | np.isclose(x, a) | np.isclose(y, 0.)
             | np.isclose(y, b))
    bk[2::DOF] = check
    # constraining u at x = 0
    check = np.isclose(x, 0.)
    bk[0::DOF] = check
    # constraining v at y = 0
    check = np.isclose(y, 0.)
    bk[1::DOF] = check

    # unconstrained nodes
    bu = ~bk  # logical_not

    Kuu = K[bu, :][:, bu]
    Muu = M[bu, :][:, bu]

    # solving generalized eigenvalue problem
    num_eigenvalues = 5
    print('eig solver begin')
    eigvals, eigvecsu = eigh(a=Kuu, b=Muu)
    print('eig solver end')
    eigvecs = np.zeros((K.shape[0], num_eigenvalues), dtype=float)
    eigvecs[bu, :] = eigvecsu[:, :num_eigenvalues]
    omegan = eigvals**0.5

    # theoretical reference
    m = 1
    n = 1
    rho = lam.rho
    D = 2 * h**3 * E / (3 * (1 - nu**2))
    wmn = (m**2 / a**2 + n**2 / b**2) * np.sqrt(D * np.pi**4 /
                                                (2 * rho * h)) / 2
    print('Theoretical omega123', wmn)
    print(omegan[:num_eigenvalues])
    assert np.isclose(omegan[0], wmn, rtol=0.01)

    if plot_mode is not None:
        import matplotlib
        matplotlib.use('TkAgg')
        import matplotlib.pyplot as plt
        plt.gca().set_aspect('equal')
        wplot = eigvecs[2::DOF, plot_mode].reshape(nx, ny).T
        levels = np.linspace(wplot.min(), wplot.max(), 300)
        plt.contourf(xmesh, ymesh, wplot, levels=levels)
        plt.colorbar()
        plt.show()
コード例 #6
0
nodes_xyz = np.array([n.pos for n in nodes])
index_ref_point = nodes_xyz.min(axis=0)

index_dist = ((nodes_xyz - index_ref_point)**2).sum(axis=-1)
indices = np.argsort(index_dist)
for i, node in enumerate(nodes):
    node.index = indices[i]

n = nodes.shape[0]
dof = 2

# material properties
E11 = 71.e9
nu = 0.33
plyt = 0.0001
lam = read_stack([0], plyt=plyt, laminaprop=(E11, E11, nu))
prop = Property(lam.A, lam.B, lam.D, lam.E)
for tria in trias:
    tria.prop = prop

#TODO allocate less memory here...
k0 = np.zeros((n*dof, n*dof), dtype=np.float64)

prop_from_node = False
count = 0
Atotal = 0
for edge in edges:
    Ac = edge.Ac
    Atotal += Ac
    ipts = edge.ipts
    for ipt in ipts:
コード例 #7
0
def test_plate_from_zero():
    # Plate geometry and laminate data

    a = 0.406
    b = 0.254
    E1 = 1.295e11
    E2 = 9.37e9
    nu12 = 0.38
    G12 = 5.24e9
    G13 = 5.24e9
    G23 = 5.24e9
    plyt = 1.9e-4
    laminaprop = (E1, E2, nu12, G12, G13, G23)

    angles = [0, 45, -45, 90, 90, -45, 45, 0]

    # Generating Mesh
    # ---

    import numpy as np
    from scipy.spatial import Delaunay

    xs = np.linspace(0, a, 8)
    ys = np.linspace(0, b, 8)
    points = np.array(np.meshgrid(xs, ys)).T.reshape(-1, 2)
    tri = Delaunay(points)

    # Using Meshless Package
    # ---

    from scipy.sparse import coo_matrix

    from composites.laminate import read_stack
    from structsolve import solve, lb
    from meshless.espim.read_mesh import read_delaunay
    from meshless.espim.plate2d_calc_k0 import calc_k0
    from meshless.espim.plate2d_calc_kG import calc_kG
    from meshless.espim.plate2d_add_k0s import add_k0s

    mesh = read_delaunay(points, tri)
    nodes = np.array(list(mesh.nodes.values()))
    prop_from_nodes = True

    nodes_xyz = np.array([n.xyz for n in nodes])

    # **Applying properties

    # applying heterogeneous properties
    for node in nodes:
        lam = read_stack(angles, plyt=plyt, laminaprop=laminaprop)
        node.prop = lam

    # **Defining Boundary Conditions**
    #

    DOF = 5

    def bc(K, mesh):
        for node in nodes[nodes_xyz[:, 0] == xs.min()]:
            for dof in [1, 3]:
                j = dof - 1
                K[node.index * DOF + j, :] = 0
                K[:, node.index * DOF + j] = 0
        for node in nodes[(nodes_xyz[:, 1] == ys.min()) |
                          (nodes_xyz[:, 1] == ys.max())]:
            for dof in [2, 3]:
                j = dof - 1
                K[node.index * DOF + j, :] = 0
                K[:, node.index * DOF + j] = 0
        for node in nodes[nodes_xyz[:, 0] == xs.max()]:
            for dof in [3]:
                j = dof - 1
                K[node.index * DOF + j, :] = 0
                K[:, node.index * DOF + j] = 0

    # **Calculating Constitutive Stiffness Matrix**

    k0s_method = 'cell-based'
    k0 = calc_k0(mesh, prop_from_nodes)
    add_k0s(k0, mesh, prop_from_nodes, k0s_method, alpha=0.2)
    bc(k0, mesh)
    k0 = coo_matrix(k0)

    # **Defining Load and External Force Vector**

    def define_loads(mesh):
        loads = []
        load_nodes = nodes[(nodes_xyz[:, 0] == xs.max())
                           & (nodes_xyz[:, 1] != ys.min()) &
                           (nodes_xyz[:, 1] != ys.max())]
        fx = -1. / (nodes[nodes_xyz[:, 0] == xs.max()].shape[0] - 1)
        for node in load_nodes:
            loads.append([node, (fx, 0, 0)])
        load_nodes = nodes[(nodes_xyz[:, 0] == xs.max()) & (
            (nodes_xyz[:, 1] == ys.min()) | (nodes_xyz[:, 1] == ys.max()))]
        fx = -1. / (nodes[nodes_xyz[:, 0] == xs.max()].shape[0] - 1) / 2
        for node in load_nodes:
            loads.append([node, (fx, 0, 0)])
        return loads

    n = k0.shape[0] // DOF
    fext = np.zeros(n * DOF, dtype=np.float64)
    loads = define_loads(mesh)
    for node, force_xyz in loads:
        fext[node.index * DOF + 0] = force_xyz[0]
    print('Checking sum of forces: %s' %
          str(fext.reshape(-1, DOF).sum(axis=0)))

    # **Running Static Analysis**

    d = solve(k0, fext, silent=True)
    total_trans = (d[0::DOF]**2 + d[1::DOF]**2)**0.5
    print('Max total translation', total_trans.max())

    # **Calculating Geometric Stiffness Matrix**

    kG = calc_kG(d, mesh, prop_from_nodes)
    bc(kG, mesh)
    kG = coo_matrix(kG)

    # **Running Linear Buckling Analysis**

    eigvals, eigvecs = lb(k0, kG, silent=True)
    print('First 5 eigenvalues')
    print('\n'.join(map(str, eigvals[:5])))

    assert np.allclose(eigvals[:5], [
        1004.29332981,
        1822.11577078,
        2898.3728806,
        2947.17499169,
        3297.54959342,
    ])