Пример #1
0
    def get_shape_functions(self, N2):
        N2 = np.array(N2, dtype=np.int32)
        inclusions = self.conf['inclusions']
        params = self.conf['params']
        positions = self.conf['positions']
        chars = []
        for ii, incl in enumerate(inclusions):
            position = positions[ii]
            if isinstance(position, np.ndarray):
                SS = get_shift_inclusion(N2, position, self.Y)

            if incl in inclusion_keys['cube']:
                h = params[ii]
                Wraw = get_weights_con(h, N2, self.Y)
                chars.append(np.real(DFT.ifftnc(SS*Wraw, N2))*np.prod(N2))
            elif incl in inclusion_keys['ball']:
                r = params[ii]/2
                if r == 0:
                    Wraw = np.zeros(N2)
                else:
                    Wraw = get_weights_circ(r, N2, self.Y)
                chars.append(np.real(DFT.ifftnc(SS*Wraw, N2))*np.prod(N2))
            elif incl == 'all':
                chars.append(np.ones(N2))
            elif incl == 'otherwise':
                chars.append(np.ones(N2))
                for ii in np.arange(len(inclusions)-1):
                    chars[-1] -= chars[ii]
            else:
                msg = 'The inclusion (%s) is not supported!' % (incl)
                raise NotImplementedError(msg)
        return chars
Пример #2
0
    def get_A_Ga(self, Nbar, primaldual='primal', order=None, P=None):
        """ Returns stiffness matrix for scheme with exact integration."""

        if order is None and 'order' in self.conf:
            order = self.conf['order']

        if order is None:
            shape_funs = self.get_shape_functions(Nbar)
            val = np.zeros(self.conf['vals'][0].shape + shape_funs[0].shape)
            for ii in range(len(self.conf['inclusions'])):
                if primaldual is 'primal':
                    Aincl = self.conf['vals'][ii]
                elif primaldual is 'dual':
                    Aincl = np.linalg.inv(self.conf['vals'][ii])
                val += np.einsum('ij...,k...->ijk...', Aincl, shape_funs[ii])
            return Matrix(name='A_Ga', val=val, Fourier=False)

        else:
            if P is None and 'P' in self.conf:
                P = self.conf['P']
            coord = Grid.get_coordinates(P, self.Y)
            vals = self.evaluate(coord)
            dim = vals.d
            if primaldual is 'dual':
                vals = vals.inv()

            h = self.Y/P
            if order in [0, 'constant']:
                Wraw = get_weights_con(h, Nbar, self.Y)
            elif order in [1, 'bilinear']:
                Wraw = get_weights_lin(h, Nbar, self.Y)

            Aapp = np.zeros(np.hstack([dim, dim, Nbar]))
            for m in np.arange(dim):
                for n in np.arange(dim):
                    hAM0 = DFT.fftnc(vals[m, n], P)
                    if np.allclose(P, Nbar):
                        hAM = hAM0
                    elif np.all(np.greater_equal(P, Nbar)):
                        hAM = decrease(hAM0, Nbar)
                    elif np.all(np.less(P, Nbar)):
                        factor = np.ceil(np.array(Nbar, dtype=np.float64) / P)
                        hAM0per = np.tile(hAM0, 2*factor-1)
                        hAM = decrease(hAM0per, Nbar)
                    else:
                        raise ValueError()

                    pNbar = np.prod(Nbar)
                    """ if DFT is normalized in accordance with articles there
                    should be np.prod(M) instead of np.prod(Nbar)"""
                    Aapp[m, n] = np.real(pNbar*DFT.ifftnc(Wraw*hAM, Nbar))

            name = 'A_Ga_o%d_P%d' % (order, P.max())
            return Matrix(name=name, val=Aapp, Fourier=False)
Пример #3
0
    def get_shape_functions(self, N2):
        """
        Returns stiffness matrix for exact integration scheme for individual
        inclusions (square, circle, etc.).
        """
        N2 = np.array(N2, dtype=np.int32)
        inclusions = self.conf['inclusions']
        params = self.conf['params']
        positions = self.conf['positions']

        chars = []
        for ii, incl in enumerate(inclusions):
            position = positions[ii]
            if isinstance(position, np.ndarray):
                SS = get_shift_inclusion(N2, position, self.Y)

            if incl in inclusion_keys['cube']:
                Wraw = get_weights_con(params[ii], N2, self.Y)
                chars.append(np.real(DFT.ifftnc(SS * Wraw, N2)) * np.prod(N2))

            elif incl in inclusion_keys['ball']:
                r = params[ii] / 2
                if r == 0:
                    Wraw = np.zeros(N2)
                else:
                    Wraw = get_weights_circ(r, N2, self.Y)
                chars.append(np.real(DFT.ifftnc(SS * Wraw, N2)) * np.prod(N2))

            elif incl in inclusion_keys['pyramid']:
                Wraw = get_weights_lin(params[ii] / 2., N2, self.Y)
                chars.append(np.real(DFT.ifftnc(SS * Wraw, N2)) * np.prod(N2))

            elif incl == 'all':
                chars.append(np.ones(N2))

            elif incl == 'otherwise':
                chars.append(np.ones(N2))
                for ii in np.arange(len(inclusions) - 1):
                    chars[-1] -= chars[ii]

            else:
                msg = 'The inclusion (%s) is not supported!' % (incl)
                raise NotImplementedError(msg)

        return chars
Пример #4
0
def elasticity(problem):
    """
    Homogenization of linear elasticity.

    Parameters
    ----------
    problem : object
    """
    print ' '
    pb = problem
    print pb

    # Fourier projections
    _, hG1hN, hG1sN, hG2hN, hG2sN = proj.elasticity(pb.solve['N'],
                                                    pb.Y,
                                                    centered=True,
                                                    NyqNul=True)
    del _

    if pb.solve['kind'] is 'GaNi':
        Nbar = pb.solve['N']
    elif pb.solve['kind'] is 'Ga':
        Nbar = 2 * pb.solve['N'] - 1
        hG1hN = hG1hN.enlarge(Nbar)
        hG1sN = hG1sN.enlarge(Nbar)
        hG2hN = hG2hN.enlarge(Nbar)
        hG2sN = hG2sN.enlarge(Nbar)

    FN = DFT(name='FN', inverse=False, N=Nbar)
    FiN = DFT(name='FiN', inverse=True, N=Nbar)

    G1N = LinOper(name='G1', mat=[[FiN, hG1hN + hG1sN, FN]])
    G2N = LinOper(name='G2', mat=[[FiN, hG2hN + hG2sN, FN]])

    for primaldual in pb.solve['primaldual']:
        print '\nproblem: ' + primaldual
        solutions = np.zeros(pb.shape).tolist()
        results = np.zeros(pb.shape).tolist()

        # material coefficients
        mat = Material(pb.material)

        if pb.solve['kind'] is 'GaNi':
            A = mat.get_A_GaNi(pb.solve['N'], primaldual)
        elif pb.solve['kind'] is 'Ga':
            A = mat.get_A_Ga(Nbar=Nbar, primaldual=primaldual)

        if primaldual is 'primal':
            GN = G1N
        else:
            GN = G2N

        Afun = LinOper(name='FiGFA', mat=[[GN, A]])

        D = pb.dim * (pb.dim + 1) / 2
        for iL in np.arange(D):  # iteration over unitary loads
            E = np.zeros(D)
            E[iL] = 1
            print 'macroscopic load E = ' + str(E)
            EN = VecTri(name='EN', macroval=E, N=Nbar, Fourier=False)
            # initial approximation for solvers
            x0 = VecTri(N=Nbar, d=D, Fourier=False)

            B = Afun(-EN)  # RHS

            if not hasattr(pb.solver, 'callback'):
                cb = CallBack(A=Afun, B=B)
            elif pb.solver['callback'] == 'detailed':
                cb = CallBack_GA(A=Afun, B=B, EN=EN, A_Ga=A, GN=GN)
            else:
                raise NotImplementedError("The solver callback (%s) is not \
                    implemented" % (pb.solver['callback']))

            print 'solver : %s' % pb.solver['kind']
            X, info = linear_solver(solver=pb.solver['kind'],
                                    Afun=Afun,
                                    B=B,
                                    x0=x0,
                                    par=pb.solver,
                                    callback=cb)

            solutions[iL] = add_macro2minimizer(X, E)
            results[iL] = {'cb': cb, 'info': info}
            print cb

        # POSTPROCESSING
        del Afun, B, E, EN, GN, X
        postprocess(pb, A, mat, solutions, results, primaldual)
Пример #5
0
    def get_A_Ga(self, Nbar, primaldual='primal', order=-1, P=None):
        """
        Returns stiffness matrix for scheme with exact integration.
        """
        if order == -1:
            if 'order' in self.conf:
                order = self.conf['order']
            else:
                raise ValueError('The material order is undefined!')
        elif order not in [None, 'exact', 0, 1]:
            raise ValueError('Wrong material order (%s)!' % str(order))

        if order in [None, 'exact']:
            shape_funs = self.get_shape_functions(Nbar)
            val = np.zeros(self.conf['vals'][0].shape + shape_funs[0].shape)
            for ii in range(len(self.conf['inclusions'])):
                if primaldual is 'primal':
                    Aincl = self.conf['vals'][ii]
                elif primaldual is 'dual':
                    Aincl = np.linalg.inv(self.conf['vals'][ii])
                val += np.einsum('ij...,k...->ijk...', Aincl, shape_funs[ii])
            name = 'A_Ga'

        else:
            if P is None and 'P' in self.conf:
                P = self.conf['P']
            coord = Grid.get_coordinates(P, self.Y)
            vals = self.evaluate(coord)
            dim = vals.d
            if primaldual is 'dual':
                vals = vals.inv()

            h = self.Y / P
            if order in [0, 'constant']:
                Wraw = get_weights_con(h, Nbar, self.Y)
            elif order in [1, 'bilinear']:
                Wraw = get_weights_lin(h, Nbar, self.Y)

            val = np.zeros(np.hstack([dim, dim, Nbar]))
            for m in np.arange(dim):
                for n in np.arange(dim):
                    hAM0 = DFT.fftnc(vals[m, n], P)
                    if np.allclose(P, Nbar):
                        hAM = hAM0
                    elif np.all(np.greater_equal(P, Nbar)):
                        hAM = decrease(hAM0, Nbar)
                    elif np.all(np.less(P, Nbar)):
                        factor = np.ceil(np.array(Nbar, dtype=np.float64) / P)
                        hAM0per = np.tile(hAM0, 2 * factor - 1)
                        hAM = decrease(hAM0per, Nbar)
                    else:
                        raise ValueError()

                    pNbar = np.prod(Nbar)
                    """ if DFT is normalized in accordance with articles there
                    should be np.prod(M) instead of np.prod(Nbar)"""
                    val[m, n] = np.real(pNbar * DFT.ifftnc(Wraw * hAM, Nbar))

            name = 'A_Ga_o%d_P%d' % (order, P.max())

        return Matrix(name=name, val=val, Fourier=False)