コード例 #1
0
    def console_output(self, xopt, image_file):


        self.topology_factory.update_topology(xopt)
        tup = (2*self.topology_factory.a, 2*self.topology_factory.b)
        print('The element dimensions are (um): %gx%g' % tup)
        params = self.topology_factory.get_params()
        cantilever = microfem.Cantilever(*params)
        microfem.plot_topology(cantilever, image_file)

        if self.topology_factory.is_connected is True:

            fem = microfem.PlateFEM(self.material, cantilever)
            coords = (cantilever.xtip, cantilever.ytip)
            opr = microfem.PlateDisplacement(fem, coords).get_operator()
            mode_ident = microfem.ModeIdentification(fem, cantilever, 'plate')

            w, _, vall = fem.modal_analysis(self.n_modes)
            freq = np.sqrt(w) / (2*np.pi)
            kuu = fem.get_stiffness_matrix(free=False)
            phis = [vall[:, [i]] for i in range(self.n_modes)]
            wtips = [opr @ p for p in phis]
            kfunc = lambda p, w: np.asscalar(p.T @ kuu @ p / w ** 2)
            ks = [kfunc(p, w) for p, w in zip(phis, wtips)]
            types = [mode_ident.is_mode_flexural(p) for p in phis]

            tup = ('Disp', 'Freq (Hz)', 'Stiffness', 'Flexural')
            print('\n    %-15s %-15s %-15s %-10s' % tup)
            for i in range(self.n_modes):
                tup = (i, wtips[i], freq[i], ks[i], str(types[i]))
                print('%-2d: %-15g %-15g %-15g %-10s' % tup)

            for i in range(self.n_modes):
                microfem.plot_mode(fem, vall[:, i])
コード例 #2
0
    def objective_function(self, xs):

        self.topology_factory.update_topology(xs)

        if self.topology_factory.is_connected is True:

            params = self.topology_factory.get_params()
            cantilever = microfem.Cantilever(*params)
            fem = microfem.PlateFEM(self.material, cantilever)
            coords = (cantilever.xtip, cantilever.ytip)
            opr = microfem.PlateDisplacement(fem, coords).get_operator()
            mode_ident = microfem.ModeIdentification(fem, cantilever, 'plate')

            try:
                w, _, vall = fem.modal_analysis(1)
            except RuntimeError:
                print('singular')
            kuu = fem.get_stiffness_matrix(free=False)
            f1 = np.asscalar(np.sqrt(w) / (2 * np.pi))
            phi1 = vall[:, [0]]
            wtip1 = np.asscalar(opr @ phi1)
            kfunc = lambda p, w: np.asscalar(p.T @ kuu @ p / w**2)
            k1 = kfunc(phi1, wtip1)
            type1 = mode_ident.is_mode_flexural(phi1)

            if type1 is False:
                cost = 1e8
            else:
                cost = -f1 * 1e-6 if k1 < self.k1 else k1

            return (cost, )

        return (self.topology_factory.connectivity_penalty, )
コード例 #3
0
    def objective_function(self, xs):

        self.topology_factory.update_topology(xs)
        a = self.topology_factory.a
        b = self.topology_factory.b

        if self.topology_factory.is_connected is True:

            topology = self.topology_factory.topology
            cantilever = microfem.Cantilever(topology, a, b)
            fem = microfem.PlateFEM(self.material, cantilever)
            coords = (cantilever.xtip, cantilever.ytip)
            opr = PlateDisplacement(fem, coords).get_operator()
            mode_ident = ModeIdentification(fem, cantilever)

            w, _, vall = fem.modal_analysis(self.n_modes)
            kuu = fem.get_stiffness_matrix(free=False)
            phi = vall[:, [0]]
            wtip = opr @ phi
            f1 = np.asscalar(np.sqrt(w) / (2 * np.pi))
            k1 = np.asscalar(phi.T @ kuu @ phi / wtip**2)
            type_ = mode_ident.is_mode_flexural(phi)
            cost = (-f1, k1) if type_ is True else (1e8, 1e8)
            return cost

        return (self.topology_factory.connectivity_penalty,
                self.topology_factory.connectivity_penalty)
コード例 #4
0
    def objective_function(self, xs):

        self.topology_factory.update_topology(xs)

        if self.topology_factory.is_connected is True:

            params = self.topology_factory.get_params()
            cantilever = microfem.Cantilever(*params)
            fem = microfem.PlateFEM(self.material, cantilever)
            coords = (cantilever.xtip, cantilever.ytip)
            opr = microfem.PlateDisplacement(fem, coords).get_operator()
            mode_ident = microfem.ModeIdentification(fem, cantilever, 'plate')

            w, _, vall = fem.modal_analysis(self.n_modes)
            kuu = fem.get_stiffness_matrix(free=False)
            fs = np.sqrt(w) / (2*np.pi)
            phis = [vall[:, [i]] for i in range(self.n_modes)]
            wtips = [opr @ p for p in phis]
            kfunc = lambda p, w: np.asscalar(p.T @ kuu @ p / w ** 2)
            ks = [kfunc(p, w) for p, w in zip(phis, wtips)]
            types = [mode_ident.is_mode_flexural(p) for p in phis]

            if types[0] is False:
                cost = 1e8
            elif types[1] is True:
                cost = self.evaluation(fs[0], fs[1], ks[0], ks[1])
            elif types[2] is True:
                cost = self.evaluation(fs[0], fs[2], ks[0], ks[2])
            else:
                cost = 2e7

            return (cost,)

        return (self.topology_factory.connectivity_penalty,)
コード例 #5
0
    def console_output(self, xopt, image_file):
        
        self.topology_factory.update_topology(xopt)
        topology = self.topology_factory.topology
        cantilever = microfem.Cantilever(topology, self.a, self.b)
        microfem.plot_topology(cantilever, image_file)
        
        if self.topology_factory.is_connected is True:
            
            fem = microfem.PlateFEM(self.material, cantilever)
            coords = (cantilever.xtip, cantilever.ytip)
            opr = PlateDisplacement(fem, coords).get_operator()
            mode_ident = ModeIdentification(fem, cantilever)
            
            w, _, vall = fem.modal_analysis(self.n_modes)
            freq = np.sqrt(w) / (2*np.pi)
            kuu = fem.get_stiffness_matrix(free=False)
            phis = [vall[:, [i]] for i in range(self.n_modes)]
            wtips = [opr @ p for p in phis]
            ks = [np.asscalar(p.T @ kuu @ p / w ** 2) for p, w in zip(phis, wtips)]
            costs = [k / ks[0] for k in ks]
            types = [mode_ident.is_mode_flexural(p) for p in phis]
            
            tup = ('Disp', 'Freq (Hz)', 'Stiffness', 'Ratio', 'Flexural')
            print('\n    %-15s %-15s %-15s %-15s %-10s' % tup)
            for i in range(self.n_modes):
                tup = (i, wtips[i], freq[i], ks[i], costs[i], str(types[i]))
                print('%-2d: %-15g %-15g %-15g %-15g %-10s' % tup)

            for i in range(self.n_modes):
                microfem.plot_mode(fem, vall[:, i])
                
コード例 #6
0
    def objective_function(self, xs):
        """
        Evaluates the objective function. The objective function calculates 
        the ratio between the dynamic stiffness of the flexural modes with
        respect to the first.
        
        Parameters
        ----------
        xs : list of floats      
            The optimization design variables for a solution.
            
        Returns
        -------
        : float       
            The evaluated objective for the solution.
        """

        self.topology_factory.update_topology(np.array(xs))
        topology = self.topology_factory.topology

        if self.topology_factory.is_connected is True:

            cost = self.problem.objective_function(topology)

            # Initialize new FEM and other analyses.
            cantilever = microfem.Cantilever(topology, self.a, self.b)
            self.fem.update_mesh(cantilever)
            coords = (cantilever.xtip, cantilever.ytip)
            pd = PlateDisplacement(self.fem, coords)
            opr = pd.get_operator()
            mode_ident = ModeIdentification(self.fem, cantilever)

            # Perform modal analysis and retrieve the stiffness matrix.
            w, _, vall = self.fem.modal_analysis(self.n_modes)
            kuu = self.fem.get_stiffness_matrix(free=False)

            # Analyze the first mode.
            phi1 = vall[:, [0]]
            wtip1 = opr @ phi1
            k1 = np.asscalar(phi1.T @ kuu @ phi1 / wtip1**2)

            cost, ratio_index, ratios = 0, 0, [2, 3, 4]
            for i in range(1, self.n_modes):
                if ratio_index < (self.n_ratio - 1):
                    phi = vall[:, [i]]
                    if mode_ident.is_mode_flexural(phi) == True:
                        wtip = opr @ phi
                        k = np.asscalar(phi.T @ kuu @ phi / wtip**2)
                        cost += (k / k1 - ratios[ratio_index])**2
                        ratio_index += 1

            return (cost, )

        return (self.topology_factory.connectivity_penalty, )
コード例 #7
0
    def console_output(self, xopt, image_file):

        self.topology_factory.update_topology(xopt)
        params = self.topology_factory.get_params()
        cantilever = microfem.Cantilever(*params)
        microfem.plot_topology(cantilever, image_file)

        if self.topology_factory.is_connected is True:

            fem = microfem.PlateFEM(self.material, cantilever)
            w, _, vall = fem.modal_analysis(1)
            f = np.asscalar(np.sqrt(w) / (2 * np.pi))
            print('The first modal frequency is (Hz): %g' % f)
            microfem.plot_mode(fem, vall[:, 0])
コード例 #8
0
    def objective_function(self, xs):

        self.topology_factory.update_topology(xs)

        if self.topology_factory.is_connected is True:

            params = self.topology_factory.get_params()
            cantilever = microfem.Cantilever(*params)
            fem = microfem.PlateFEM(self.material, cantilever)
            w, _, _ = fem.modal_analysis(1)
            f = np.asscalar(np.sqrt(w) / (2 * np.pi))
            cost = abs(f - self.f0)

            return (cost, )

        return (self.topology_factory.connectivity_penalty, )
コード例 #9
0
    def to_console_final(self, xopt):

        print()
        print('--- Solution Characteristics ---')
        if self.exe_time != 0:
            print('Time (s): %g' % (self.exe_time))

        self.topology_factory.update_topology(xopt)
        topology = self.topology_factory.topology
        cantilever = microfem.Cantilever(topology, self.a, self.b)
        fn = ''.join((self.dir, '/', self.tag, '-image.png'))
        microfem.plot_topology(cantilever, fn)

        if self.topology_factory.is_connected is True:

            self.fem.update_mesh(cantilever)
            coords = (cantilever.xtip, cantilever.ytip)
            opr = PlateDisplacement(self.fem, coords).get_operator()
            mode_ident = ModeIdentification(self.fem, cantilever)

            w, _, vall = self.fem.modal_analysis(self.n_modes)
            freq = np.sqrt(w) / (2 * np.pi)
            kuu = self.fem.get_stiffness_matrix(free=False)
            phis = [vall[:, [i]] for i in range(self.n_modes)]
            wtips = [opr @ p for p in phis]
            ks = [
                np.asscalar(p.T @ kuu @ p / w**2) for p, w in zip(phis, wtips)
            ]
            costs = [k / ks[0] for k in ks]
            types = [mode_ident.is_mode_flexural(p) for p in phis]

            tup = ('Disp', 'Freq (Hz)', 'Stiffness', 'Ratio', 'Flexural')
            print('\n    %-15s %-15s %-15s %-15s %-10s' % tup)
            for i in range(self.n_modes):
                tup = (i, wtips[i], freq[i], ks[i], costs[i], str(types[i]))
                print('%-2d: %-15g %-15g %-15g %-15g %-10s' % tup)

            for i in range(self.n_modes):
                microfem.plot_mode(self.fem, vall[:, i])
コード例 #10
0
#params = {'nelx': 30, 'nely': 60, 'a0': 10e-6, 'b0':10e-6}
#top = PowerTopology(params)

#params = {'nelx': 30, 'nely': 60, 'a0': 5e-6, 'b0':5e-6}
#top = NewRectangleTopology(params)
#top = NewSplitTopology(params)
#top = NewSteppedTopology(params)
#top = NewPowerTopology(params)
#top = NewTwoStructuresTopology(params)

params = {
    'support_ratio': 3.0,
    'nknx': 5,
    'nkny': 10,
    'nelx': 40,
    'nely': 80,
    'pcon1': 1.0e7,
    'pcon2': 1.0e3,
    'a0': 5.0e-6,
    'b0': 5.0e-6
}
top = NewCompactTopology(params)

for i in range(1):
    xs = 2 * np.random.random(top.ind_size) - 1.0
    top.update_topology(xs)
    cantilever = microfem.Cantilever(*top.get_params())
    #print(xs)
    print(top.xtip, top.ytip)
    microfem.plot_topology(cantilever)
コード例 #11
0
# Along with the topology, the size of each element needs to be defined. `a`
# is half the element width in the x-direction (rows) and `b` is half the
# element length in the y-direction (cols). The units are in um.
a = 5
b = 5

# One option for normalising the mode shapes is to normalize with respect to
# the deflection at a point on the cantilever. The coordinates are in um and
# should be on a solid element.
xtip = 250
ytip = 495

# Combine the above parameters into a Cantilever object in the microfem
# package. Information about the cantilever can be displayed and the topology
# can be plotted.
cantilever = microfem.Cantilever(topology, a, b, xtip, ytip)
cantilever.to_console()
microfem.plot_topology(cantilever)

material = microfem.PiezoMumpsMaterial()
fem = microfem.LaminateFEM(material, cantilever)

# With the FEM model buitl, modal analysis can be performed. This returns the
# resonance frequencies and mode shapes of the cantilever. These can then be
# plotted.
n_modes = 3
ws, _, vall = fem.modal_analysis(n_modes=n_modes)

# Using the results of the modal analysis, the frequency, stiffness,
# tip displacement, and mode type (flexural, torsional), can be determined.
coords = (cantilever.xtip, cantilever.ytip)