def run(domain, order): omega = domain.create_region('Omega', 'all') bbox = domain.get_mesh_bounding_box() min_x, max_x = bbox[:, 0] min_y, max_y = bbox[:, 1] eps = 1e-8 * (max_x - min_x) gamma1 = domain.create_region('Gamma1', 'vertices in (x < %.10f)' % (min_x + eps), 'facet') gamma2 = domain.create_region('Gamma2', 'vertices in (x > %.10f)' % (max_x - eps), 'facet') gamma3 = domain.create_region('Gamma3', 'vertices in y < %.10f' % (min_y + eps), 'facet') gamma4 = domain.create_region('Gamma4', 'vertices in y > %.10f' % (max_y - eps), 'facet') field = Field.from_args('fu', nm.float64, 1, omega, approx_order=order) u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') integral = Integral('i', order=2*order) t1 = Term.new('dw_laplace(v, u)', integral, omega, v=v, u=u) eq = Equation('eq', t1) eqs = Equations([eq]) fix1 = EssentialBC('fix1', gamma1, {'u.0' : 0.4}) fix2 = EssentialBC('fix2', gamma2, {'u.0' : 0.0}) def get_shift(ts, coors, region): return nm.ones_like(coors[:, 0]) dof_map_fun = Function('dof_map_fun', per.match_x_line) shift_fun = Function('shift_fun', get_shift) sper = LinearCombinationBC('sper', [gamma3, gamma4], {'u.0' : 'u.0'}, dof_map_fun, 'shifted_periodic', arguments=(shift_fun,)) ls = ScipyDirect({}) pb = Problem('laplace', equations=eqs, auto_solvers=None) pb.time_update(ebcs=Conditions([fix1, fix2]), lcbcs=Conditions([sper])) ev = pb.get_evaluator() nls = Newton({}, lin_solver=ls, fun=ev.eval_residual, fun_grad=ev.eval_tangent_matrix) pb.set_solver(nls) state = pb.solve() return pb, state
def test_solving(self): from sfepy.base.base import IndexedStruct from sfepy.discrete import (FieldVariable, Material, Problem, Function, Equation, Equations, Integral) from sfepy.discrete.conditions import Conditions, EssentialBC from sfepy.terms import Term from sfepy.solvers.ls import ScipyDirect from sfepy.solvers.nls import Newton from sfepy.mechanics.matcoefs import stiffness_from_lame u = FieldVariable('u', 'unknown', self.field) v = FieldVariable('v', 'test', self.field, primary_var_name='u') m = Material('m', D=stiffness_from_lame(self.dim, 1.0, 1.0)) f = Material('f', val=[[0.02], [0.01]]) bc_fun = Function('fix_u_fun', fix_u_fun, extra_args={'extra_arg' : 'hello'}) fix_u = EssentialBC('fix_u', self.gamma1, {'u.all' : bc_fun}) shift_u = EssentialBC('shift_u', self.gamma2, {'u.0' : 0.1}) integral = Integral('i', order=3) t1 = Term.new('dw_lin_elastic(m.D, v, u)', integral, self.omega, m=m, v=v, u=u) t2 = Term.new('dw_volume_lvf(f.val, v)', integral, self.omega, f=f, v=v) eq = Equation('balance', t1 + t2) eqs = Equations([eq]) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) pb = Problem('elasticity', equations=eqs) ## pb.save_regions_as_groups('regions') pb.set_bcs(ebcs=Conditions([fix_u, shift_u])) pb.set_solver(nls) state = pb.solve() name = op.join(self.options.out_dir, 'test_high_level_solving.vtk') pb.save_state(name, state) ok = nls_status.condition == 0 if not ok: self.report('solver did not converge!') _ok = state.has_ebc() if not _ok: self.report('EBCs violated!') ok = ok and _ok return ok
def solveLaplaceEquationTetrahedral(mesh, meshVTK, boundaryPoints, boundaryConditions): """ mesh: path to a 3D mesh / sfepy mesh """ if isinstance(mesh, str): mesh = Mesh.from_file(mesh) #Set domains domain = FEDomain('domain', mesh) omega = domain.create_region('Omega', 'all') boundary = domain.create_region( 'gamma', 'vertex %s' % ','.join(map(str, range(meshVTK.GetNumberOfPoints()))), 'facet') #set fields field = Field.from_args('fu', np.float64, 1, omega, approx_order=1) u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') m = Material('m', val=[1.]) #Define element integrals integral = Integral('i', order=3) #Equations defining t1 = Term.new('dw_laplace( v, u )', integral, omega, v=v, u=u) eq = Equation('balance', t1) eqs = Equations([eq]) heatBoundary = boundaryConditions points = boundaryPoints #Boundary conditions c = ClosestPointStupid(points, heatBoundary, meshVTK) def u_fun(ts, coors, bc=None, problem=None, c=c): c.distances = [] v = np.zeros(len(coors)) for i, p in enumerate(coors): v[i] = c.interpolate(p) #c.findClosestPoint(p) return v bc_fun = Function('u_fun', u_fun) fix1 = EssentialBC('fix_u', boundary, {'u.all': bc_fun}) #Solve problem ls = ScipyDirect({}) nls = Newton({}, lin_solver=ls) pb = Problem('heat', equations=eqs) pb.set_bcs(ebcs=Conditions([fix1])) pb.set_solver(nls) state = pb.solve(verbose=False, save_results=False) u = state.get_parts()['u'] return u
def run(domain, order): omega = domain.create_region('Omega', 'all') bbox = domain.get_mesh_bounding_box() min_x, max_x = bbox[:, 0] min_y, max_y = bbox[:, 1] eps = 1e-8 * (max_x - min_x) gamma1 = domain.create_region('Gamma1', 'vertices in (x < %.10f)' % (min_x + eps), 'facet') gamma2 = domain.create_region('Gamma2', 'vertices in (x > %.10f)' % (max_x - eps), 'facet') gamma3 = domain.create_region('Gamma3', 'vertices in y < %.10f' % (min_y + eps), 'facet') gamma4 = domain.create_region('Gamma4', 'vertices in y > %.10f' % (max_y - eps), 'facet') field = Field.from_args('fu', nm.float64, 1, omega, approx_order=order) u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') integral = Integral('i', order=2 * order) t1 = Term.new('dw_laplace(v, u)', integral, omega, v=v, u=u) eq = Equation('eq', t1) eqs = Equations([eq]) fix1 = EssentialBC('fix1', gamma1, {'u.0': 0.4}) fix2 = EssentialBC('fix2', gamma2, {'u.0': 0.0}) def get_shift(ts, coors, region): return nm.ones_like(coors[:, 0]) dof_map_fun = Function('dof_map_fun', per.match_x_line) shift_fun = Function('shift_fun', get_shift) sper = LinearCombinationBC('sper', [gamma3, gamma4], {'u.0': 'u.0'}, dof_map_fun, 'shifted_periodic', arguments=(shift_fun, )) ls = ScipyDirect({}) nls = Newton({}, lin_solver=ls) pb = Problem('laplace', equations=eqs) pb.set_bcs(ebcs=Conditions([fix1, fix2]), lcbcs=Conditions([sper])) pb.set_solver(nls) state = pb.solve() return pb, state
def make_h1_projection_data(target, eval_data): """ Project scalar data given by a material-like `eval_data()` function to a scalar `target` field variable using the :math:`H^1` dot product. """ order = target.field.approx_order * 2 integral = Integral('i', order=order) un = target.name v = FieldVariable('v', 'test', target.field, primary_var_name=un) lhs1 = Term.new('dw_volume_dot(v, %s)' % un, integral, target.field.region, v=v, **{un: target}) lhs2 = Term.new('dw_laplace(v, %s)' % un, integral, target.field.region, v=v, **{un: target}) def _eval_data(ts, coors, mode, **kwargs): if mode == 'qp': val = eval_data(ts, coors, mode, 'val', **kwargs) gval = eval_data(ts, coors, mode, 'grad', **kwargs) return {'val': val, 'gval': gval} m = Material('m', function=_eval_data) rhs1 = Term.new('dw_volume_lvf(m.val, v)', integral, target.field.region, m=m, v=v) rhs2 = Term.new('dw_diffusion_r(m.gval, v)', integral, target.field.region, m=m, v=v) eq = Equation('projection', lhs1 + lhs2 - rhs1 - rhs2) eqs = Equations([eq]) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) pb = Problem('aux', equations=eqs) pb.set_solver(nls) # This sets the target variable with the projection solution. pb.solve(save_results=False) if nls_status.condition != 0: output('H1 projection: solver did not converge!')
def solve_problem(shape, dims, young, poisson, force, transform=None): domain = make_domain(dims[:2], shape, transform=transform) omega = domain.regions['Omega'] gamma1 = domain.regions['Gamma1'] gamma2 = domain.regions['Gamma2'] field = Field.from_args('fu', nm.float64, 6, omega, approx_order=1, poly_space_base='shell10x') u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') thickness = dims[2] if transform is None: pload = [[0.0, 0.0, force / shape[1], 0.0, 0.0, 0.0]] * shape[1] elif transform == 'bend': pload = [[force / shape[1], 0.0, 0.0, 0.0, 0.0, 0.0]] * shape[1] elif transform == 'twist': pload = [[0.0, force / shape[1], 0.0, 0.0, 0.0, 0.0]] * shape[1] m = Material('m', D=sh.create_elastic_tensor(young=young, poisson=poisson), values={'.drill' : 1e-7}) load = Material('load', values={'.val' : pload}) aux = Integral('i', order=3) qp_coors, qp_weights = aux.get_qp('3_8') qp_coors[:, 2] = thickness * (qp_coors[:, 2] - 0.5) qp_weights *= thickness integral = Integral('i', coors=qp_coors, weights=qp_weights, order='custom') t1 = Term.new('dw_shell10x(m.D, m.drill, v, u)', integral, omega, m=m, v=v, u=u) t2 = Term.new('dw_point_load(load.val, v)', integral, gamma2, load=load, v=v) eq = Equation('balance', t1 - t2) eqs = Equations([eq]) fix_u = EssentialBC('fix_u', gamma1, {'u.all' : 0.0}) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) pb = Problem('elasticity with shell10x', equations=eqs) pb.set_bcs(ebcs=Conditions([fix_u])) pb.set_solver(nls) state = pb.solve() return pb, state, u, gamma2
def run(domain, order): omega = domain.create_region("Omega", "all") bbox = domain.get_mesh_bounding_box() min_x, max_x = bbox[:, 0] min_y, max_y = bbox[:, 1] eps = 1e-8 * (max_x - min_x) gamma1 = domain.create_region("Gamma1", "vertices in (x < %.10f)" % (min_x + eps), "facet") gamma2 = domain.create_region("Gamma2", "vertices in (x > %.10f)" % (max_x - eps), "facet") gamma3 = domain.create_region("Gamma3", "vertices in y < %.10f" % (min_y + eps), "facet") gamma4 = domain.create_region("Gamma4", "vertices in y > %.10f" % (max_y - eps), "facet") field = Field.from_args("fu", nm.float64, 1, omega, approx_order=order) u = FieldVariable("u", "unknown", field) v = FieldVariable("v", "test", field, primary_var_name="u") integral = Integral("i", order=2 * order) t1 = Term.new("dw_laplace(v, u)", integral, omega, v=v, u=u) eq = Equation("eq", t1) eqs = Equations([eq]) fix1 = EssentialBC("fix1", gamma1, {"u.0": 0.4}) fix2 = EssentialBC("fix2", gamma2, {"u.0": 0.0}) def get_shift(ts, coors, region): return nm.ones_like(coors[:, 0]) dof_map_fun = Function("dof_map_fun", per.match_x_line) shift_fun = Function("shift_fun", get_shift) sper = LinearCombinationBC( "sper", [gamma3, gamma4], {"u.0": "u.0"}, dof_map_fun, "shifted_periodic", arguments=(shift_fun,) ) ls = ScipyDirect({}) pb = Problem("laplace", equations=eqs, auto_solvers=None) pb.time_update(ebcs=Conditions([fix1, fix2]), lcbcs=Conditions([sper])) ev = pb.get_evaluator() nls = Newton({}, lin_solver=ls, fun=ev.eval_residual, fun_grad=ev.eval_tangent_matrix) pb.set_solver(nls) state = pb.solve() return pb, state
def linear_projection(pb, cval): from sfepy.discrete import (FieldVariable, Material, Integral, Equation, Equations, Problem) from sfepy.discrete.fem import Mesh, FEDomain, Field from sfepy.terms import Term from sfepy.solvers.ls import ScipyDirect from sfepy.solvers.nls import Newton from sfepy.base.base import IndexedStruct mesh = Mesh.from_file(pb.conf.filename_mesh) domain = FEDomain('domain', mesh) omega = domain.create_region('Omega', 'all') field = Field.from_args('scf', nm.float64, 'scalar', omega, approx_order=1) g = FieldVariable('g', 'unknown', field) f = FieldVariable('f', 'test', field, primary_var_name='g') integral = Integral('i', order=2) m = Material('m', function=set_grad) t1 = Term.new('dw_volume_dot(f, g)', integral, omega, f=f, g=g) t2 = Term.new('dw_volume_lvf(m.cs, f)', integral, omega, m=m, f=f) eq = Equation('balance', t1 - t2) eqs = Equations([eq]) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({'eps_a': 1e-15}, lin_solver=ls, status=nls_status) pb = Problem('elasticity', equations=eqs) pb.set_solver(nls) out = nm.empty((g.n_dof, cval.shape[2]), dtype=nm.float64) for ii in range(cval.shape[2]): pb.data = nm.ascontiguousarray(cval[:, :, ii, :]) pb.time_update() state = pb.solve() out[:, ii] = state.get_parts()['g'] return out
def main(): from sfepy import data_dir parser = ArgumentParser(description=__doc__, formatter_class=RawDescriptionHelpFormatter) parser.add_argument('--version', action='version', version='%(prog)s') parser.add_argument('--young', metavar='float', type=float, action='store', dest='young', default=2000.0, help=helps['young']) parser.add_argument('--poisson', metavar='float', type=float, action='store', dest='poisson', default=0.4, help=helps['poisson']) parser.add_argument('--load', metavar='float', type=float, action='store', dest='load', default=-1000.0, help=helps['load']) parser.add_argument('--order', metavar='int', type=int, action='store', dest='order', default=1, help=helps['order']) parser.add_argument('-r', '--refine', metavar='int', type=int, action='store', dest='refine', default=0, help=helps['refine']) parser.add_argument('-s', '--show', action="store_true", dest='show', default=False, help=helps['show']) parser.add_argument('-p', '--probe', action="store_true", dest='probe', default=False, help=helps['probe']) options = parser.parse_args() assert_((0.0 < options.poisson < 0.5), "Poisson's ratio must be in ]0, 0.5[!") assert_((0 < options.order), 'displacement approximation order must be at least 1!') output('using values:') output(" Young's modulus:", options.young) output(" Poisson's ratio:", options.poisson) output(' vertical load:', options.load) output('uniform mesh refinement level:', options.refine) # Build the problem definition. mesh = Mesh.from_file(data_dir + '/meshes/2d/its2D.mesh') domain = FEDomain('domain', mesh) if options.refine > 0: for ii in range(options.refine): output('refine %d...' % ii) domain = domain.refine() output('... %d nodes %d elements' % (domain.shape.n_nod, domain.shape.n_el)) omega = domain.create_region('Omega', 'all') left = domain.create_region('Left', 'vertices in x < 0.001', 'facet') bottom = domain.create_region('Bottom', 'vertices in y < 0.001', 'facet') top = domain.create_region('Top', 'vertex 2', 'vertex') field = Field.from_args('fu', nm.float64, 'vector', omega, approx_order=options.order) u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') D = stiffness_from_youngpoisson(2, options.young, options.poisson) asphalt = Material('Asphalt', D=D) load = Material('Load', values={'.val' : [0.0, options.load]}) integral = Integral('i', order=2*options.order) integral0 = Integral('i', order=0) t1 = Term.new('dw_lin_elastic(Asphalt.D, v, u)', integral, omega, Asphalt=asphalt, v=v, u=u) t2 = Term.new('dw_point_load(Load.val, v)', integral0, top, Load=load, v=v) eq = Equation('balance', t1 - t2) eqs = Equations([eq]) xsym = EssentialBC('XSym', bottom, {'u.1' : 0.0}) ysym = EssentialBC('YSym', left, {'u.0' : 0.0}) ls = AutoDirect({}) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) pb = Problem('elasticity', equations=eqs) pb.set_bcs(ebcs=Conditions([xsym, ysym])) pb.set_solver(nls) # Solve the problem. state = pb.solve() output(nls_status) # Postprocess the solution. out = state.create_output_dict() out = stress_strain(out, pb, state, extend=True) pb.save_state('its2D_interactive.vtk', out=out) gdata = geometry_data['2_3'] nc = len(gdata.coors) integral_vn = Integral('ivn', coors=gdata.coors, weights=[gdata.volume / nc] * nc) nodal_stress(out, pb, state, integrals=Integrals([integral_vn])) if options.probe: # Probe the solution. probes, labels = gen_lines(pb) sfield = Field.from_args('sym_tensor', nm.float64, 3, omega, approx_order=options.order - 1) stress = FieldVariable('stress', 'parameter', sfield, primary_var_name='(set-to-None)') strain = FieldVariable('strain', 'parameter', sfield, primary_var_name='(set-to-None)') cfield = Field.from_args('component', nm.float64, 1, omega, approx_order=options.order - 1) component = FieldVariable('component', 'parameter', cfield, primary_var_name='(set-to-None)') ev = pb.evaluate order = 2 * (options.order - 1) strain_qp = ev('ev_cauchy_strain.%d.Omega(u)' % order, mode='qp') stress_qp = ev('ev_cauchy_stress.%d.Omega(Asphalt.D, u)' % order, mode='qp', copy_materials=False) project_by_component(strain, strain_qp, component, order) project_by_component(stress, stress_qp, component, order) all_results = [] for ii, probe in enumerate(probes): fig, results = probe_results(u, strain, stress, probe, labels[ii]) fig.savefig('its2D_interactive_probe_%d.png' % ii) all_results.append(results) for ii, results in enumerate(all_results): output('probe %d:' % ii) output.level += 2 for key, res in ordered_iteritems(results): output(key + ':') val = res[1] output(' min: %+.2e, mean: %+.2e, max: %+.2e' % (val.min(), val.mean(), val.max())) output.level -= 2 if options.show: # Show the solution. If the approximation order is greater than 1, the # extra DOFs are simply thrown away. from sfepy.postprocess.viewer import Viewer view = Viewer('its2D_interactive.vtk') view(vector_mode='warp_norm', rel_scaling=1, is_scalar_bar=True, is_wireframe=True)
def main(): parser = ArgumentParser(description=__doc__.rstrip(), formatter_class=RawDescriptionHelpFormatter) parser.add_argument('output_dir', help=helps['output_dir']) parser.add_argument('--dims', metavar='dims', action='store', dest='dims', default='1.0,1.0,1.0', help=helps['dims']) parser.add_argument('--shape', metavar='shape', action='store', dest='shape', default='7,7,7', help=helps['shape']) parser.add_argument('--centre', metavar='centre', action='store', dest='centre', default='0.0,0.0,0.0', help=helps['centre']) parser.add_argument('-3', '--3d', action='store_true', dest='is_3d', default=False, help=helps['3d']) parser.add_argument('--order', metavar='int', type=int, action='store', dest='order', default=1, help=helps['order']) options = parser.parse_args() dim = 3 if options.is_3d else 2 dims = nm.array(eval(options.dims), dtype=nm.float64)[:dim] shape = nm.array(eval(options.shape), dtype=nm.int32)[:dim] centre = nm.array(eval(options.centre), dtype=nm.float64)[:dim] output('dimensions:', dims) output('shape: ', shape) output('centre: ', centre) mesh0 = gen_block_mesh(dims, shape, centre, name='block-fem', verbose=True) domain0 = FEDomain('d', mesh0) bbox = domain0.get_mesh_bounding_box() min_x, max_x = bbox[:, 0] eps = 1e-8 * (max_x - min_x) cnt = (shape[0] - 1) // 2 g0 = 0.5 * dims[0] grading = nm.array([g0 / 2**ii for ii in range(cnt)]) + eps + centre[0] - g0 domain, subs = refine_towards_facet(domain0, grading, 'x <') omega = domain.create_region('Omega', 'all') gamma1 = domain.create_region('Gamma1', 'vertices in (x < %.10f)' % (min_x + eps), 'facet') gamma2 = domain.create_region('Gamma2', 'vertices in (x > %.10f)' % (max_x - eps), 'facet') field = Field.from_args('fu', nm.float64, 1, omega, approx_order=options.order) if subs is not None: field.substitute_dofs(subs) u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') integral = Integral('i', order=2*options.order) t1 = Term.new('dw_laplace(v, u)', integral, omega, v=v, u=u) eq = Equation('eq', t1) eqs = Equations([eq]) def u_fun(ts, coors, bc=None, problem=None): """ Define a displacement depending on the y coordinate. """ if coors.shape[1] == 2: min_y, max_y = bbox[:, 1] y = (coors[:, 1] - min_y) / (max_y - min_y) val = (max_y - min_y) * nm.cos(3 * nm.pi * y) else: min_y, max_y = bbox[:, 1] min_z, max_z = bbox[:, 2] y = (coors[:, 1] - min_y) / (max_y - min_y) z = (coors[:, 2] - min_z) / (max_z - min_z) val = ((max_y - min_y) * (max_z - min_z) * nm.cos(3 * nm.pi * y) * (1.0 + 3.0 * (z - 0.5)**2)) return val bc_fun = Function('u_fun', u_fun) fix1 = EssentialBC('shift_u', gamma1, {'u.0' : bc_fun}) fix2 = EssentialBC('fix2', gamma2, {'u.all' : 0.0}) ls = ScipyDirect({}) nls = Newton({}, lin_solver=ls) pb = Problem('heat', equations=eqs) pb.set_bcs(ebcs=Conditions([fix1, fix2])) pb.set_solver(nls) state = pb.solve() if subs is not None: field.restore_dofs() filename = os.path.join(options.output_dir, 'hanging.vtk') ensure_path(filename) pb.save_state(filename, state) if options.order > 1: pb.save_state(filename, state, linearization=Struct(kind='adaptive', min_level=0, max_level=8, eps=1e-3))
def make_l2_projection_data(target, eval_data, order=None, ls=None, nls_options=None): """ Project scalar data to a scalar `target` field variable using the :math:`L^2` dot product. Parameters ---------- target : FieldVariable instance The target variable. eval_data : callable or array Either a material-like function `eval_data()`, or an array of values in quadrature points that has to be reshapable to the shape required by `order`. order : int, optional The quadrature order. If not given, it is set to `2 * target.field.approx_order`. """ if order is None: order = 2 * target.field.approx_order integral = Integral('i', order=order) un = FieldVariable('u', 'unknown', target.field) v = FieldVariable('v', 'test', un.field, primary_var_name=un.name) lhs = Term.new('dw_volume_dot(v, %s)' % un.name, integral, un.field.region, v=v, **{un.name: un}) def _eval_data(ts, coors, mode, **kwargs): if mode == 'qp': if callable(eval_data): val = eval_data(ts, coors, mode, **kwargs) else: val = eval_data.reshape((coors.shape[0], 1, 1)) return {'val': val} m = Material('m', function=_eval_data) rhs = Term.new('dw_volume_lvf(m.val, v)', integral, un.field.region, m=m, v=v) eq = Equation('projection', lhs - rhs) eqs = Equations([eq]) if ls is None: ls = ScipyDirect({}) if nls_options is None: nls_options = {} nls_status = IndexedStruct() nls = Newton(nls_options, lin_solver=ls, status=nls_status) pb = Problem('aux', equations=eqs) pb.set_solver(nls) # This sets the un variable with the projection solution. pb.solve(save_results=False) # Copy the projection solution to target. target.set_data(un()) if nls_status.condition != 0: output('L2 projection: solver did not converge!')
def main(): from sfepy import data_dir parser = ArgumentParser(description=__doc__, formatter_class=RawDescriptionHelpFormatter) parser.add_argument('--version', action='version', version='%(prog)s') parser.add_argument('--young', metavar='float', type=float, action='store', dest='young', default=2000.0, help=helps['young']) parser.add_argument('--poisson', metavar='float', type=float, action='store', dest='poisson', default=0.4, help=helps['poisson']) parser.add_argument('--load', metavar='float', type=float, action='store', dest='load', default=-1000.0, help=helps['load']) parser.add_argument('--order', metavar='int', type=int, action='store', dest='order', default=1, help=helps['order']) parser.add_argument('-r', '--refine', metavar='int', type=int, action='store', dest='refine', default=0, help=helps['refine']) parser.add_argument('-s', '--show', action="store_true", dest='show', default=False, help=helps['show']) parser.add_argument('-p', '--probe', action="store_true", dest='probe', default=False, help=helps['probe']) options = parser.parse_args() assert_((0.0 < options.poisson < 0.5), "Poisson's ratio must be in ]0, 0.5[!") assert_((0 < options.order), 'displacement approximation order must be at least 1!') output('using values:') output(" Young's modulus:", options.young) output(" Poisson's ratio:", options.poisson) output(' vertical load:', options.load) output('uniform mesh refinement level:', options.refine) # Build the problem definition. mesh = Mesh.from_file(data_dir + '/meshes/2d/its2D.mesh') domain = FEDomain('domain', mesh) if options.refine > 0: for ii in range(options.refine): output('refine %d...' % ii) domain = domain.refine() output('... %d nodes %d elements' % (domain.shape.n_nod, domain.shape.n_el)) omega = domain.create_region('Omega', 'all') left = domain.create_region('Left', 'vertices in x < 0.001', 'facet') bottom = domain.create_region('Bottom', 'vertices in y < 0.001', 'facet') top = domain.create_region('Top', 'vertex 2', 'vertex') field = Field.from_args('fu', nm.float64, 'vector', omega, approx_order=options.order) u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') D = stiffness_from_youngpoisson(2, options.young, options.poisson) asphalt = Material('Asphalt', D=D) load = Material('Load', values={'.val': [0.0, options.load]}) integral = Integral('i', order=2 * options.order) integral0 = Integral('i', order=0) t1 = Term.new('dw_lin_elastic(Asphalt.D, v, u)', integral, omega, Asphalt=asphalt, v=v, u=u) t2 = Term.new('dw_point_load(Load.val, v)', integral0, top, Load=load, v=v) eq = Equation('balance', t1 - t2) eqs = Equations([eq]) xsym = EssentialBC('XSym', bottom, {'u.1': 0.0}) ysym = EssentialBC('YSym', left, {'u.0': 0.0}) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) pb = Problem('elasticity', equations=eqs) pb.set_bcs(ebcs=Conditions([xsym, ysym])) pb.set_solver(nls) # Solve the problem. state = pb.solve() output(nls_status) # Postprocess the solution. out = state.create_output_dict() out = stress_strain(out, pb, state, extend=True) pb.save_state('its2D_interactive.vtk', out=out) gdata = geometry_data['2_3'] nc = len(gdata.coors) integral_vn = Integral('ivn', coors=gdata.coors, weights=[gdata.volume / nc] * nc) nodal_stress(out, pb, state, integrals=Integrals([integral_vn])) if options.probe: # Probe the solution. probes, labels = gen_lines(pb) sfield = Field.from_args('sym_tensor', nm.float64, 3, omega, approx_order=options.order - 1) stress = FieldVariable('stress', 'parameter', sfield, primary_var_name='(set-to-None)') strain = FieldVariable('strain', 'parameter', sfield, primary_var_name='(set-to-None)') cfield = Field.from_args('component', nm.float64, 1, omega, approx_order=options.order - 1) component = FieldVariable('component', 'parameter', cfield, primary_var_name='(set-to-None)') ev = pb.evaluate order = 2 * (options.order - 1) strain_qp = ev('ev_cauchy_strain.%d.Omega(u)' % order, mode='qp') stress_qp = ev('ev_cauchy_stress.%d.Omega(Asphalt.D, u)' % order, mode='qp', copy_materials=False) project_by_component(strain, strain_qp, component, order) project_by_component(stress, stress_qp, component, order) all_results = [] for ii, probe in enumerate(probes): fig, results = probe_results(u, strain, stress, probe, labels[ii]) fig.savefig('its2D_interactive_probe_%d.png' % ii) all_results.append(results) for ii, results in enumerate(all_results): output('probe %d:' % ii) output.level += 2 for key, res in ordered_iteritems(results): output(key + ':') val = res[1] output(' min: %+.2e, mean: %+.2e, max: %+.2e' % (val.min(), val.mean(), val.max())) output.level -= 2 if options.show: # Show the solution. If the approximation order is greater than 1, the # extra DOFs are simply thrown away. from sfepy.postprocess.viewer import Viewer view = Viewer('its2D_interactive.vtk') view(vector_mode='warp_norm', rel_scaling=1, is_scalar_bar=True, is_wireframe=True)
def main(cli_args): dims = parse_argument_list(cli_args.dims, float) shape = parse_argument_list(cli_args.shape, int) centre = parse_argument_list(cli_args.centre, float) material_parameters = parse_argument_list(cli_args.material_parameters, float) order = cli_args.order ts_vals = cli_args.ts.split(',') ts = { 't0': float(ts_vals[0]), 't1': float(ts_vals[1]), 'n_step': int(ts_vals[2]) } do_plot = cli_args.plot ### Mesh and regions ### mesh = gen_block_mesh(dims, shape, centre, name='block', verbose=False) domain = FEDomain('domain', mesh) omega = domain.create_region('Omega', 'all') lbn, rtf = domain.get_mesh_bounding_box() box_regions = define_box_regions(3, lbn, rtf) regions = dict( [[r, domain.create_region(r, box_regions[r][0], box_regions[r][1])] for r in box_regions]) ### Fields ### scalar_field = Field.from_args('fu', np.float64, 'scalar', omega, approx_order=order - 1) vector_field = Field.from_args('fv', np.float64, 'vector', omega, approx_order=order) u = FieldVariable('u', 'unknown', vector_field, history=1) v = FieldVariable('v', 'test', vector_field, primary_var_name='u') p = FieldVariable('p', 'unknown', scalar_field, history=1) q = FieldVariable('q', 'test', scalar_field, primary_var_name='p') ### Material ### c10, c01 = material_parameters m = Material( 'm', mu=2 * c10, kappa=2 * c01, ) ### Boundary conditions ### x_sym = EssentialBC('x_sym', regions['Left'], {'u.0': 0.0}) y_sym = EssentialBC('y_sym', regions['Near'], {'u.1': 0.0}) z_sym = EssentialBC('z_sym', regions['Bottom'], {'u.2': 0.0}) disp_fun = Function('disp_fun', get_displacement) displacement = EssentialBC('displacement', regions['Right'], {'u.0': disp_fun}) ebcs = Conditions([x_sym, y_sym, z_sym, displacement]) ### Terms and equations ### integral = Integral('i', order=2 * order) term_neohook = Term.new('dw_tl_he_neohook(m.mu, v, u)', integral, omega, m=m, v=v, u=u) term_mooney = Term.new('dw_tl_he_mooney_rivlin(m.kappa, v, u)', integral, omega, m=m, v=v, u=u) term_pressure = Term.new('dw_tl_bulk_pressure(v, u, p)', integral, omega, v=v, u=u, p=p) term_volume_change = Term.new('dw_tl_volume(q, u)', integral, omega, q=q, u=u, term_mode='volume') term_volume = Term.new('dw_volume_integrate(q)', integral, omega, q=q) eq_balance = Equation('balance', term_neohook + term_mooney + term_pressure) eq_volume = Equation('volume', term_volume_change - term_volume) equations = Equations([eq_balance, eq_volume]) ### Solvers ### ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({'i_max': 5}, lin_solver=ls, status=nls_status) ### Problem ### pb = Problem('hyper', equations=equations) pb.set_bcs(ebcs=ebcs) pb.set_ics(ics=Conditions([])) tss = SimpleTimeSteppingSolver(ts, nls=nls, context=pb) pb.set_solver(tss) ### Solution ### axial_stress = [] axial_displacement = [] def stress_strain_fun(*args, **kwargs): return stress_strain(*args, order=order, global_stress=axial_stress, global_displacement=axial_displacement, **kwargs) pb.solve(save_results=True, post_process_hook=stress_strain_fun) if do_plot: plot_graphs(material_parameters, axial_stress, axial_displacement, undeformed_length=dims[0])
def main(): parser = ArgumentParser(description=__doc__.rstrip(), formatter_class=RawDescriptionHelpFormatter) parser.add_argument('-o', '--output-dir', default='.', help=helps['output_dir']) parser.add_argument('--R1', metavar='R1', action='store', dest='R1', default='0.5', help=helps['R1']) parser.add_argument('--R2', metavar='R2', action='store', dest='R2', default='1.0', help=helps['R2']) parser.add_argument('--C1', metavar='C1', action='store', dest='C1', default='0.0,0.0', help=helps['C1']) parser.add_argument('--C2', metavar='C2', action='store', dest='C2', default='0.0,0.0', help=helps['C2']) parser.add_argument('--order', metavar='int', type=int, action='store', dest='order', default=2, help=helps['order']) parser.add_argument('-v', '--viewpatch', action='store_true', dest='viewpatch', default=False, help=helps['viewpatch']) options = parser.parse_args() # Creation of the NURBS-patch with igakit R1 = eval(options.R1) R2 = eval(options.R2) C1 = list(eval(options.C1)) C2 = list(eval(options.C2)) order = options.order viewpatch = options.viewpatch create_patch(R1, R2, C1, C2, order=order, viewpatch=viewpatch) # Setting a Domain instance filename_domain = data_dir + '/meshes/iga/concentric_circles.iga' domain = IGDomain.from_file(filename_domain) # Sub-domains omega = domain.create_region('Omega', 'all') Gamma_out = domain.create_region('Gamma_out', 'vertices of set xi01', kind='facet') Gamma_in = domain.create_region('Gamma_in', 'vertices of set xi00', kind='facet') # Field (featuring order elevation) order_increase = order - domain.nurbs.degrees[0] order_increase *= int(order_increase > 0) field = Field.from_args('fu', nm.float64, 'scalar', omega, approx_order='iga', space='H1', poly_space_base='iga') # Variables u = FieldVariable('u', 'unknown', field) # unknown function v = FieldVariable('v', 'test', field, primary_var_name='u') # test function # Integral integral = Integral('i', order=2 * field.approx_order) # Term t = Term.new('dw_laplace( v, u )', integral, omega, v=v, u=u) # Equation eq = Equation('laplace', t) eqs = Equations([eq]) # Boundary Conditions u_in = EssentialBC('u_in', Gamma_in, {'u.all': 7.0}) u_out = EssentialBC('u_out', Gamma_out, {'u.all': 3.0}) # solvers ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) # problem instance pb = Problem('potential', equations=eqs, active_only=True) # Set boundary conditions pb.set_bcs(ebcs=Conditions([u_in, u_out])) # solving pb.set_solver(nls) status = IndexedStruct() state = pb.solve(status=status, save_results=True, verbose=True) # Saving the results to a classic VTK file filename = os.path.join(options.output_dir, 'concentric_circles.vtk') ensure_path(filename) pb.save_state(filename, state)
def main(): from sfepy import data_dir parser = ArgumentParser(description=__doc__, formatter_class=RawDescriptionHelpFormatter) parser.add_argument('--version', action='version', version='%(prog)s') parser.add_argument('--diffusivity', metavar='float', type=float, action='store', dest='diffusivity', default=1e-5, help=helps['diffusivity']) parser.add_argument('--ic-max', metavar='float', type=float, action='store', dest='ic_max', default=2.0, help=helps['ic_max']) parser.add_argument('--order', metavar='int', type=int, action='store', dest='order', default=2, help=helps['order']) parser.add_argument('-r', '--refine', metavar='int', type=int, action='store', dest='refine', default=0, help=helps['refine']) parser.add_argument('-p', '--probe', action="store_true", dest='probe', default=False, help=helps['probe']) parser.add_argument('-s', '--show', action="store_true", dest='show', default=False, help=helps['show']) options = parser.parse_args() assert_((0 < options.order), 'temperature approximation order must be at least 1!') output('using values:') output(' diffusivity:', options.diffusivity) output(' max. IC value:', options.ic_max) output('uniform mesh refinement level:', options.refine) mesh = Mesh.from_file(data_dir + '/meshes/3d/cylinder.mesh') domain = FEDomain('domain', mesh) if options.refine > 0: for ii in range(options.refine): output('refine %d...' % ii) domain = domain.refine() output('... %d nodes %d elements' % (domain.shape.n_nod, domain.shape.n_el)) omega = domain.create_region('Omega', 'all') left = domain.create_region('Left', 'vertices in x < 0.00001', 'facet') right = domain.create_region('Right', 'vertices in x > 0.099999', 'facet') field = Field.from_args('fu', nm.float64, 'scalar', omega, approx_order=options.order) T = FieldVariable('T', 'unknown', field, history=1) s = FieldVariable('s', 'test', field, primary_var_name='T') m = Material('m', diffusivity=options.diffusivity * nm.eye(3)) integral = Integral('i', order=2*options.order) t1 = Term.new('dw_diffusion(m.diffusivity, s, T)', integral, omega, m=m, s=s, T=T) t2 = Term.new('dw_volume_dot(s, dT/dt)', integral, omega, s=s, T=T) eq = Equation('balance', t1 + t2) eqs = Equations([eq]) # Boundary conditions. ebc1 = EssentialBC('T1', left, {'T.0' : 2.0}) ebc2 = EssentialBC('T2', right, {'T.0' : -2.0}) # Initial conditions. def get_ic(coors, ic): x, y, z = coors.T return 2 - 40.0 * x + options.ic_max * nm.sin(4 * nm.pi * x / 0.1) ic_fun = Function('ic_fun', get_ic) ic = InitialCondition('ic', omega, {'T.0' : ic_fun}) pb = Problem('heat', equations=eqs) pb.set_bcs(ebcs=Conditions([ebc1, ebc2])) pb.set_ics(Conditions([ic])) state0 = pb.get_initial_state() init_fun, prestep_fun, _poststep_fun = pb.get_tss_functions(state0) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({'is_linear' : True}, lin_solver=ls, status=nls_status) tss = SimpleTimeSteppingSolver({'t0' : 0.0, 't1' : 100.0, 'n_step' : 11}, nls=nls, context=pb, verbose=True) pb.set_solver(tss) if options.probe: # Prepare probe data. probes, labels = gen_probes(pb) ev = pb.evaluate order = 2 * (options.order - 1) gfield = Field.from_args('gu', nm.float64, 'vector', omega, approx_order=options.order - 1) dvel = FieldVariable('dvel', 'parameter', gfield, primary_var_name='(set-to-None)') cfield = Field.from_args('gu', nm.float64, 'scalar', omega, approx_order=options.order - 1) component = FieldVariable('component', 'parameter', cfield, primary_var_name='(set-to-None)') nls_options = {'eps_a' : 1e-16, 'i_max' : 1} suffix = tss.ts.suffix def poststep_fun(ts, vec): _poststep_fun(ts, vec) # Probe the solution. dvel_qp = ev('ev_diffusion_velocity.%d.Omega(m.diffusivity, T)' % order, copy_materials=False, mode='qp') project_by_component(dvel, dvel_qp, component, order, nls_options=nls_options) all_results = [] for ii, probe in enumerate(probes): fig, results = probe_results(ii, T, dvel, probe, labels[ii]) all_results.append(results) plt.tight_layout() fig.savefig('time_poisson_interactive_probe_%s.png' % (suffix % ts.step), bbox_inches='tight') for ii, results in enumerate(all_results): output('probe %d (%s):' % (ii, probes[ii].name)) output.level += 2 for key, res in ordered_iteritems(results): output(key + ':') val = res[1] output(' min: %+.2e, mean: %+.2e, max: %+.2e' % (val.min(), val.mean(), val.max())) output.level -= 2 else: poststep_fun = _poststep_fun pb.time_update(tss.ts) state0.apply_ebc() # This is required if {'is_linear' : True} is passed to Newton. mtx = prepare_matrix(pb, state0) pb.try_presolve(mtx) tss_status = IndexedStruct() tss(state0.get_vec(pb.active_only), init_fun=init_fun, prestep_fun=prestep_fun, poststep_fun=poststep_fun, status=tss_status) output(tss_status) if options.show: plt.show()
def test_solving(self): from sfepy.base.base import IndexedStruct from sfepy.discrete import (FieldVariable, Material, Problem, Function, Equation, Equations, Integral) from sfepy.discrete.conditions import Conditions, EssentialBC from sfepy.terms import Term from sfepy.solvers.ls import ScipyDirect from sfepy.solvers.nls import Newton from sfepy.mechanics.matcoefs import stiffness_from_lame u = FieldVariable('u', 'unknown', self.field) v = FieldVariable('v', 'test', self.field, primary_var_name='u') m = Material('m', D=stiffness_from_lame(self.dim, 1.0, 1.0)) f = Material('f', val=[[0.02], [0.01]]) bc_fun = Function('fix_u_fun', fix_u_fun, extra_args={'extra_arg': 'hello'}) fix_u = EssentialBC('fix_u', self.gamma1, {'u.all': bc_fun}) shift_u = EssentialBC('shift_u', self.gamma2, {'u.0': 0.1}) integral = Integral('i', order=3) t1 = Term.new('dw_lin_elastic(m.D, v, u)', integral, self.omega, m=m, v=v, u=u) t2 = Term.new('dw_volume_lvf(f.val, v)', integral, self.omega, f=f, v=v) eq = Equation('balance', t1 + t2) eqs = Equations([eq]) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) pb = Problem('elasticity', equations=eqs) ## pb.save_regions_as_groups('regions') pb.set_bcs(ebcs=Conditions([fix_u, shift_u])) pb.set_solver(nls) state = pb.solve() name = op.join(self.options.out_dir, 'test_high_level_solving.vtk') pb.save_state(name, state) ok = nls_status.condition == 0 if not ok: self.report('solver did not converge!') _ok = state.has_ebc() if not _ok: self.report('EBCs violated!') ok = ok and _ok return ok
# ------------------ # | Create solver | # ------------------ ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({'is_linear': True}, lin_solver=ls, status=nls_status) tss_conf = {'t0': t0, 't1': t1, 'n_step': tn, 'limiters': {"dgfu": limiter}} tss = TVDRK3StepSolver(tss_conf, nls=nls, context=pb, verbose=True) # --------- # | Solve | # --------- pb.set_solver(tss) state_end = pb.solve() output("Solved equation \n\n\t\t u_t - div(f(u))) = 0\n") output(f"With IC: {ic_fun.name}") # output("and EBCs: {}".format(pb.ebcs.names)) # output("and EPBCS: {}".format(pb.epbcs.names)) output("-------------------------------------") output(f"Approximation order is {approx_order}") output(f"Space divided into {mesh.n_el} cells, " + f"{len(mesh.coors)} steps, step size is {dx}") output(f"Time divided into {tn - 1} nodes, {tn} steps, step size is {dt}") output(f"CFL coefficient was {CFL} and " + f"order correction {1 / (2 * approx_order + 1)}") output(f"Courant number c = max(abs(u)) * dt/dx = {max_velo * dtdx}") output("------------------------------------------")
'u.[0,1]': 0.0, 'u.[2]': -z_displacement }) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) # 'i_max': 1, 'eps_a': 1e-10 pb = Problem('elasticity', equations=eqs) pb.save_regions_as_groups('regions') pb.set_bcs(ebcs=Conditions([fix_bot, fix_top])) pb.set_solver(nls) status = IndexedStruct() state = pb.solve(status=status) strain = pb.evaluate('ev_cauchy_strain.2.Omega(u)', u=u, mode='el_avg') stress = pb.evaluate('ev_cauchy_stress.2.Omega(m.D, u)', m=m, u=u, mode='el_avg') vms = get_von_mises_stress(stress.squeeze()) np.savetxt('tmp_vms.dat', vms) vms = np.loadtxt('tmp_vms.dat') vol = mesh.cmesh.get_volumes(3) np.savetxt('tmp_vol.dat', vol)
def main(): from sfepy import data_dir parser = ArgumentParser() parser.add_argument('--version', action='version', version='%(prog)s') parser.add_argument('-s', '--show', action="store_true", dest='show', default=False, help=helps['show']) options = parser.parse_args() mesh = Mesh.from_file(data_dir + '/meshes/2d/rectangle_tri.mesh') domain = FEDomain('domain', mesh) min_x, max_x = domain.get_mesh_bounding_box()[:, 0] eps = 1e-8 * (max_x - min_x) omega = domain.create_region('Omega', 'all') gamma1 = domain.create_region('Gamma1', 'vertices in x < %.10f' % (min_x + eps), 'facet') gamma2 = domain.create_region('Gamma2', 'vertices in x > %.10f' % (max_x - eps), 'facet') field = Field.from_args('fu', nm.float64, 'vector', omega, approx_order=2) u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') m = Material('m', D=stiffness_from_lame(dim=2, lam=1.0, mu=1.0)) f = Material('f', val=[[0.02], [0.01]]) integral = Integral('i', order=3) t1 = Term.new('dw_lin_elastic(m.D, v, u)', integral, omega, m=m, v=v, u=u) t2 = Term.new('dw_volume_lvf(f.val, v)', integral, omega, f=f, v=v) eq = Equation('balance', t1 + t2) eqs = Equations([eq]) fix_u = EssentialBC('fix_u', gamma1, {'u.all': 0.0}) bc_fun = Function('shift_u_fun', shift_u_fun, extra_args={'shift': 0.01}) shift_u = EssentialBC('shift_u', gamma2, {'u.0': bc_fun}) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) pb = Problem('elasticity', equations=eqs) pb.save_regions_as_groups('regions') pb.set_bcs(ebcs=Conditions([fix_u, shift_u])) pb.set_solver(nls) status = IndexedStruct() state = pb.solve(status=status) print('Nonlinear solver status:\n', nls_status) print('Stationary solver status:\n', status) pb.save_state('linear_elasticity.vtk', state) if options.show: view = Viewer('linear_elasticity.vtk') view(vector_mode='warp_norm', rel_scaling=2, is_scalar_bar=True, is_wireframe=True)
def _solve(self, property_array): """ Solve the Sfepy problem for one sample. Args: property_array: array of shape (n_x, n_y, 2) where the last index is for Lame's parameter and shear modulus, respectively. Returns: the strain field of shape (n_x, n_y, 2) where the last index represents the x and y displacements """ shape = property_array.shape[:-1] mesh = self._get_mesh(shape) domain = Domain('domain', mesh) region_all = domain.create_region('region_all', 'all') field = Field.from_args('fu', np.float64, 'vector', region_all, # pylint: disable=no-member approx_order=2) u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') m = self._get_material(property_array, domain) integral = Integral('i', order=4) t1 = Term.new('dw_lin_elastic_iso(m.lam, m.mu, v, u)', integral, region_all, m=m, v=v, u=u) eq = Equation('balance_of_forces', t1) eqs = Equations([eq]) epbcs, functions = self._get_periodicBCs(domain) ebcs = self._get_displacementBCs(domain) lcbcs = self._get_linear_combinationBCs(domain) ls = ScipyDirect({}) pb = Problem('elasticity', equations=eqs, auto_solvers=None) pb.time_update( ebcs=ebcs, epbcs=epbcs, lcbcs=lcbcs, functions=functions) ev = pb.get_evaluator() nls = Newton({}, lin_solver=ls, fun=ev.eval_residual, fun_grad=ev.eval_tangent_matrix) try: pb.set_solvers_instances(ls, nls) except AttributeError: pb.set_solver(nls) vec = pb.solve() u = vec.create_output_dict()['u'].data u_reshape = np.reshape(u, (tuple(x + 1 for x in shape) + u.shape[-1:])) dims = domain.get_mesh_bounding_box().shape[1] strain = np.squeeze( pb.evaluate( 'ev_cauchy_strain.{dim}.region_all(u)'.format( dim=dims), mode='el_avg', copy_materials=False)) strain_reshape = np.reshape(strain, (shape + strain.shape[-1:])) stress = np.squeeze( pb.evaluate( 'ev_cauchy_stress.{dim}.region_all(m.D, u)'.format( dim=dims), mode='el_avg', copy_materials=False)) stress_reshape = np.reshape(stress, (shape + stress.shape[-1:])) return strain_reshape, u_reshape, stress_reshape
def main(argv=None): options = parse_args(argv=argv) # vvvvvvvvvvvvvvvv # approx_order = 2 # ^^^^^^^^^^^^^^^^ # # Setup output names outputs_folder = options.output_dir domain_name = "domain_1D" problem_name = "iburgers_1D" output_folder = pjoin(outputs_folder, problem_name, str(approx_order)) output_format = "vtk" save_timestn = 100 clear_folder(pjoin(output_folder, "*." + output_format)) configure_output({ 'output_screen': True, 'output_log_name': pjoin(output_folder, f"last_run_{problem_name}_{approx_order}.txt") }) # ------------ # | Get mesh | # ------------ X1 = 0. XN = 1. n_nod = 100 n_el = n_nod - 1 mesh = get_gen_1D_mesh_hook(X1, XN, n_nod).read(None) # ----------------------------- # | Create problem components | # ----------------------------- integral = Integral('i', order=approx_order * 2) domain = FEDomain(domain_name, mesh) omega = domain.create_region('Omega', 'all') left = domain.create_region('Gamma1', 'vertices in x == %.10f' % X1, 'vertex') right = domain.create_region('Gamma2', 'vertices in x == %.10f' % XN, 'vertex') field = DGField('dgfu', nm.float64, 'scalar', omega, approx_order=approx_order) u = FieldVariable('u', 'unknown', field, history=1) v = FieldVariable('v', 'test', field, primary_var_name='u') MassT = Term.new('dw_dot(v, u)', integral, omega, u=u, v=v) velo = nm.array(1.0) def adv_fun(u): vu = velo.T * u[..., None] return vu def adv_fun_d(u): v1 = velo.T * nm.ones(u.shape + (1, )) return v1 burg_velo = velo.T / nm.linalg.norm(velo) def burg_fun(u): vu = burg_velo * u[..., None]**2 return vu def burg_fun_d(u): v1 = 2 * burg_velo * u[..., None] return v1 StiffT = Term.new('dw_ns_dot_grad_s(fun, fun_d, u[-1], v)', integral, omega, u=u, v=v, fun=burg_fun, fun_d=burg_fun_d) # alpha = Material('alpha', val=[.0]) # FluxT = AdvectDGFluxTerm("adv_lf_flux(a.val, v, u)", "a.val, v, u[-1]", # integral, omega, u=u, v=v, a=a, alpha=alpha) FluxT = Term.new('dw_dg_nonlinear_laxfrie_flux(fun, fun_d, v, u[-1])', integral, omega, u=u, v=v, fun=burg_fun, fun_d=burg_fun_d) eq = Equation('balance', MassT - StiffT + FluxT) eqs = Equations([eq]) # ------------------------------ # | Create boundary conditions | # ------------------------------ left_fix_u = EssentialBC('left_fix_u', left, {'u.all': 1.0}) right_fix_u = EssentialBC('right_fix_u', right, {'u.all': 0.0}) # ---------------------------- # | Create initial condition | # ---------------------------- def ghump(x): """ Nice gaussian. """ return nm.exp(-200 * x**2) def ic_wrap(x, ic=None): return ghump(x - .3) ic_fun = Function('ic_fun', ic_wrap) ics = InitialCondition('ic', omega, {'u.0': ic_fun}) # ------------------ # | Create problem | # ------------------ pb = Problem(problem_name, equations=eqs, conf=Struct(options={"save_times": save_timestn}, ics={}, ebcs={}, epbcs={}, lcbcs={}, materials={}), active_only=False) pb.setup_output(output_dir=output_folder, output_format=output_format) pb.set_ics(Conditions([ics])) # ------------------ # | Create limiter | # ------------------ limiter = MomentLimiter1D # --------------------------- # | Set time discretization | # --------------------------- CFL = .2 max_velo = nm.max(nm.abs(velo)) t0 = 0 t1 = .2 dx = nm.min(mesh.cmesh.get_volumes(1)) dt = dx / max_velo * CFL / (2 * approx_order + 1) tn = int(nm.ceil((t1 - t0) / dt)) dtdx = dt / dx # ------------------ # | Create solver | # ------------------ ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({'is_linear': True}, lin_solver=ls, status=nls_status) tss_conf = { 't0': t0, 't1': t1, 'n_step': tn, 'limiters': { "dgfu": limiter } } tss = TVDRK3StepSolver(tss_conf, nls=nls, context=pb, verbose=True) # --------- # | Solve | # --------- pb.set_solver(tss) state_end = pb.solve() output("Solved equation \n\n\t\t u_t - div(f(u))) = 0\n") output(f"With IC: {ic_fun.name}") # output("and EBCs: {}".format(pb.ebcs.names)) # output("and EPBCS: {}".format(pb.epbcs.names)) output("-------------------------------------") output(f"Approximation order is {approx_order}") output(f"Space divided into {mesh.n_el} cells, " + f"{len(mesh.coors)} steps, step size is {dx}") output(f"Time divided into {tn - 1} nodes, {tn} steps, step size is {dt}") output(f"CFL coefficient was {CFL} and " + f"order correction {1 / (2 * approx_order + 1)}") output(f"Courant number c = max(abs(u)) * dt/dx = {max_velo * dtdx}") output("------------------------------------------") output(f"Time stepping solver is {tss.name}") output(f"Limiter used: {limiter.name}") output("======================================") # ---------- # | Plot 1D| # ---------- if options.plot: load_and_plot_fun(output_folder, domain_name, t0, t1, min(tn, save_timestn), ic_fun)
def main(cli_args): dims = parse_argument_list(cli_args.dims, float) shape = parse_argument_list(cli_args.shape, int) centre = parse_argument_list(cli_args.centre, float) material_parameters = parse_argument_list(cli_args.material_parameters, float) order = cli_args.order ts_vals = cli_args.ts.split(',') ts = { 't0' : float(ts_vals[0]), 't1' : float(ts_vals[1]), 'n_step' : int(ts_vals[2])} do_plot = cli_args.plot ### Mesh and regions ### mesh = gen_block_mesh( dims, shape, centre, name='block', verbose=False) domain = FEDomain('domain', mesh) omega = domain.create_region('Omega', 'all') lbn, rtf = domain.get_mesh_bounding_box() box_regions = define_box_regions(3, lbn, rtf) regions = dict([ [r, domain.create_region(r, box_regions[r][0], box_regions[r][1])] for r in box_regions]) ### Fields ### scalar_field = Field.from_args( 'fu', np.float64, 'scalar', omega, approx_order=order-1) vector_field = Field.from_args( 'fv', np.float64, 'vector', omega, approx_order=order) u = FieldVariable('u', 'unknown', vector_field, history=1) v = FieldVariable('v', 'test', vector_field, primary_var_name='u') p = FieldVariable('p', 'unknown', scalar_field, history=1) q = FieldVariable('q', 'test', scalar_field, primary_var_name='p') ### Material ### c10, c01 = material_parameters m = Material( 'm', mu=2*c10, kappa=2*c01, ) ### Boundary conditions ### x_sym = EssentialBC('x_sym', regions['Left'], {'u.0' : 0.0}) y_sym = EssentialBC('y_sym', regions['Near'], {'u.1' : 0.0}) z_sym = EssentialBC('z_sym', regions['Bottom'], {'u.2' : 0.0}) disp_fun = Function('disp_fun', get_displacement) displacement = EssentialBC( 'displacement', regions['Right'], {'u.0' : disp_fun}) ebcs = Conditions([x_sym, y_sym, z_sym, displacement]) ### Terms and equations ### integral = Integral('i', order=2*order) term_neohook = Term.new( 'dw_tl_he_neohook(m.mu, v, u)', integral, omega, m=m, v=v, u=u) term_mooney = Term.new( 'dw_tl_he_mooney_rivlin(m.kappa, v, u)', integral, omega, m=m, v=v, u=u) term_pressure = Term.new( 'dw_tl_bulk_pressure(v, u, p)', integral, omega, v=v, u=u, p=p) term_volume_change = Term.new( 'dw_tl_volume(q, u)', integral, omega, q=q, u=u, term_mode='volume') term_volume = Term.new( 'dw_volume_integrate(q)', integral, omega, q=q) eq_balance = Equation('balance', term_neohook+term_mooney+term_pressure) eq_volume = Equation('volume', term_volume_change-term_volume) equations = Equations([eq_balance, eq_volume]) ### Solvers ### ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton( {'i_max' : 5}, lin_solver=ls, status=nls_status ) ### Problem ### pb = Problem('hyper', equations=equations) pb.set_bcs(ebcs=ebcs) pb.set_ics(ics=Conditions([])) tss = SimpleTimeSteppingSolver(ts, nls=nls, context=pb) pb.set_solver(tss) ### Solution ### axial_stress = [] axial_displacement = [] def stress_strain_fun(*args, **kwargs): return stress_strain( *args, order=order, global_stress=axial_stress, global_displacement=axial_displacement, **kwargs) pb.solve(save_results=True, post_process_hook=stress_strain_fun) if do_plot: plot_graphs( material_parameters, axial_stress, axial_displacement, undeformed_length=dims[0])
def solve_problem(shape, dims, young, poisson, force, transform=None): domain = make_domain(dims[:2], shape, transform=transform) omega = domain.regions['Omega'] gamma1 = domain.regions['Gamma1'] gamma2 = domain.regions['Gamma2'] field = Field.from_args('fu', nm.float64, 6, omega, approx_order=1, poly_space_base='shell10x') u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') thickness = dims[2] if transform is None: pload = [[0.0, 0.0, force / shape[1], 0.0, 0.0, 0.0]] * shape[1] elif transform == 'bend': pload = [[force / shape[1], 0.0, 0.0, 0.0, 0.0, 0.0]] * shape[1] elif transform == 'twist': pload = [[0.0, force / shape[1], 0.0, 0.0, 0.0, 0.0]] * shape[1] m = Material('m', D=sh.create_elastic_tensor(young=young, poisson=poisson), values={'.drill': 1e-7}) load = Material('load', values={'.val': pload}) aux = Integral('i', order=3) qp_coors, qp_weights = aux.get_qp('3_8') qp_coors[:, 2] = thickness * (qp_coors[:, 2] - 0.5) qp_weights *= thickness integral = Integral('i', coors=qp_coors, weights=qp_weights, order='custom') t1 = Term.new('dw_shell10x(m.D, m.drill, v, u)', integral, omega, m=m, v=v, u=u) t2 = Term.new('dw_point_load(load.val, v)', integral, gamma2, load=load, v=v) eq = Equation('balance', t1 - t2) eqs = Equations([eq]) fix_u = EssentialBC('fix_u', gamma1, {'u.all': 0.0}) ls = use_first_available([(MUMPSSolver, {}), (ScipyDirect, {})]) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) pb = Problem('elasticity with shell10x', equations=eqs) pb.set_bcs(ebcs=Conditions([fix_u])) pb.set_solver(nls) state = pb.solve() return pb, state, u, gamma2
def main(): from sfepy import data_dir parser = ArgumentParser(description=__doc__, formatter_class=RawDescriptionHelpFormatter) parser.add_argument('--version', action='version', version='%(prog)s') parser.add_argument('--diffusivity', metavar='float', type=float, action='store', dest='diffusivity', default=1e-5, help=helps['diffusivity']) parser.add_argument('--ic-max', metavar='float', type=float, action='store', dest='ic_max', default=2.0, help=helps['ic_max']) parser.add_argument('--order', metavar='int', type=int, action='store', dest='order', default=2, help=helps['order']) parser.add_argument('-r', '--refine', metavar='int', type=int, action='store', dest='refine', default=0, help=helps['refine']) parser.add_argument('-p', '--probe', action="store_true", dest='probe', default=False, help=helps['probe']) parser.add_argument('-s', '--show', action="store_true", dest='show', default=False, help=helps['show']) options = parser.parse_args() assert_((0 < options.order), 'temperature approximation order must be at least 1!') output('using values:') output(' diffusivity:', options.diffusivity) output(' max. IC value:', options.ic_max) output('uniform mesh refinement level:', options.refine) mesh = Mesh.from_file(data_dir + '/meshes/3d/cylinder.mesh') domain = FEDomain('domain', mesh) if options.refine > 0: for ii in range(options.refine): output('refine %d...' % ii) domain = domain.refine() output('... %d nodes %d elements' % (domain.shape.n_nod, domain.shape.n_el)) omega = domain.create_region('Omega', 'all') left = domain.create_region('Left', 'vertices in x < 0.00001', 'facet') right = domain.create_region('Right', 'vertices in x > 0.099999', 'facet') field = Field.from_args('fu', nm.float64, 'scalar', omega, approx_order=options.order) T = FieldVariable('T', 'unknown', field, history=1) s = FieldVariable('s', 'test', field, primary_var_name='T') m = Material('m', diffusivity=options.diffusivity * nm.eye(3)) integral = Integral('i', order=2 * options.order) t1 = Term.new('dw_diffusion(m.diffusivity, s, T)', integral, omega, m=m, s=s, T=T) t2 = Term.new('dw_volume_dot(s, dT/dt)', integral, omega, s=s, T=T) eq = Equation('balance', t1 + t2) eqs = Equations([eq]) # Boundary conditions. ebc1 = EssentialBC('T1', left, {'T.0': 2.0}) ebc2 = EssentialBC('T2', right, {'T.0': -2.0}) # Initial conditions. def get_ic(coors, ic): x, y, z = coors.T return 2 - 40.0 * x + options.ic_max * nm.sin(4 * nm.pi * x / 0.1) ic_fun = Function('ic_fun', get_ic) ic = InitialCondition('ic', omega, {'T.0': ic_fun}) pb = Problem('heat', equations=eqs) pb.set_bcs(ebcs=Conditions([ebc1, ebc2])) pb.set_ics(Conditions([ic])) state0 = pb.get_initial_state() init_fun, prestep_fun, _poststep_fun = pb.get_tss_functions(state0) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({'is_linear': True}, lin_solver=ls, status=nls_status) tss = SimpleTimeSteppingSolver({ 't0': 0.0, 't1': 100.0, 'n_step': 11 }, nls=nls, context=pb, verbose=True) pb.set_solver(tss) if options.probe: # Prepare probe data. probes, labels = gen_lines(pb) ev = pb.evaluate order = 2 * (options.order - 1) gfield = Field.from_args('gu', nm.float64, 'vector', omega, approx_order=options.order - 1) dvel = FieldVariable('dvel', 'parameter', gfield, primary_var_name='(set-to-None)') cfield = Field.from_args('gu', nm.float64, 'scalar', omega, approx_order=options.order - 1) component = FieldVariable('component', 'parameter', cfield, primary_var_name='(set-to-None)') nls_options = {'eps_a': 1e-16, 'i_max': 1} if options.show: plt.ion() suffix = tss.ts.suffix def poststep_fun(ts, vec): _poststep_fun(ts, vec) # Probe the solution. dvel_qp = ev('ev_diffusion_velocity.%d.Omega(m.diffusivity, T)' % order, copy_materials=False, mode='qp') project_by_component(dvel, dvel_qp, component, order, nls_options=nls_options) all_results = [] for ii, probe in enumerate(probes): fig, results = probe_results(ii, T, dvel, probe, labels[ii]) all_results.append(results) plt.tight_layout() fig.savefig('time_poisson_interactive_probe_%s.png' % (suffix % ts.step), bbox_inches='tight') if options.show: plt.draw() for ii, results in enumerate(all_results): output('probe %d (%s):' % (ii, probes[ii].name)) output.level += 2 for key, res in ordered_iteritems(results): output(key + ':') val = res[1] output(' min: %+.2e, mean: %+.2e, max: %+.2e' % (val.min(), val.mean(), val.max())) output.level -= 2 else: poststep_fun = _poststep_fun pb.time_update(tss.ts) state0.apply_ebc() # This is required if {'is_linear' : True} is passed to Newton. mtx = prepare_matrix(pb, state0) pb.try_presolve(mtx) tss_status = IndexedStruct() tss(state0.get_vec(pb.active_only), init_fun=init_fun, prestep_fun=prestep_fun, poststep_fun=poststep_fun, status=tss_status) output(tss_status)
def main(): parser = ArgumentParser(description=__doc__.rstrip(), formatter_class=RawDescriptionHelpFormatter) parser.add_argument('output_dir', help=helps['output_dir']) parser.add_argument('--dims', metavar='dims', action='store', dest='dims', default='1.0,1.0,1.0', help=helps['dims']) parser.add_argument('--shape', metavar='shape', action='store', dest='shape', default='7,7,7', help=helps['shape']) parser.add_argument('--centre', metavar='centre', action='store', dest='centre', default='0.0,0.0,0.0', help=helps['centre']) parser.add_argument('-3', '--3d', action='store_true', dest='is_3d', default=False, help=helps['3d']) parser.add_argument('--order', metavar='int', type=int, action='store', dest='order', default=1, help=helps['order']) options = parser.parse_args() dim = 3 if options.is_3d else 2 dims = nm.array(eval(options.dims), dtype=nm.float64)[:dim] shape = nm.array(eval(options.shape), dtype=nm.int32)[:dim] centre = nm.array(eval(options.centre), dtype=nm.float64)[:dim] output('dimensions:', dims) output('shape: ', shape) output('centre: ', centre) mesh0 = gen_block_mesh(dims, shape, centre, name='block-fem', verbose=True) domain0 = FEDomain('d', mesh0) bbox = domain0.get_mesh_bounding_box() min_x, max_x = bbox[:, 0] eps = 1e-8 * (max_x - min_x) cnt = (shape[0] - 1) // 2 g0 = 0.5 * dims[0] grading = nm.array([g0 / 2**ii for ii in range(cnt)]) + eps + centre[0] - g0 domain, subs = refine_towards_facet(domain0, grading, 'x <') omega = domain.create_region('Omega', 'all') gamma1 = domain.create_region('Gamma1', 'vertices in (x < %.10f)' % (min_x + eps), 'facet') gamma2 = domain.create_region('Gamma2', 'vertices in (x > %.10f)' % (max_x - eps), 'facet') field = Field.from_args('fu', nm.float64, 1, omega, approx_order=options.order) if subs is not None: field.substitute_dofs(subs) u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') integral = Integral('i', order=2 * options.order) t1 = Term.new('dw_laplace(v, u)', integral, omega, v=v, u=u) eq = Equation('eq', t1) eqs = Equations([eq]) def u_fun(ts, coors, bc=None, problem=None): """ Define a displacement depending on the y coordinate. """ if coors.shape[1] == 2: min_y, max_y = bbox[:, 1] y = (coors[:, 1] - min_y) / (max_y - min_y) val = (max_y - min_y) * nm.cos(3 * nm.pi * y) else: min_y, max_y = bbox[:, 1] min_z, max_z = bbox[:, 2] y = (coors[:, 1] - min_y) / (max_y - min_y) z = (coors[:, 2] - min_z) / (max_z - min_z) val = ((max_y - min_y) * (max_z - min_z) * nm.cos(3 * nm.pi * y) * (1.0 + 3.0 * (z - 0.5)**2)) return val bc_fun = Function('u_fun', u_fun) fix1 = EssentialBC('shift_u', gamma1, {'u.0': bc_fun}) fix2 = EssentialBC('fix2', gamma2, {'u.all': 0.0}) ls = ScipyDirect({}) nls = Newton({}, lin_solver=ls) pb = Problem('heat', equations=eqs) pb.set_bcs(ebcs=Conditions([fix1, fix2])) pb.set_solver(nls) state = pb.solve() if subs is not None: field.restore_dofs() filename = os.path.join(options.output_dir, 'hanging.vtk') ensure_path(filename) pb.save_state(filename, state) if options.order > 1: pb.save_state(filename, state, linearization=Struct(kind='adaptive', min_level=0, max_level=8, eps=1e-3))
def main(): from sfepy import data_dir parser = ArgumentParser() parser.add_argument('--version', action='version', version='%(prog)s') parser.add_argument('-s', '--show', action="store_true", dest='show', default=False, help=helps['show']) options = parser.parse_args() mesh = Mesh.from_file(data_dir + '/meshes/2d/rectangle_tri.mesh') domain = FEDomain('domain', mesh) min_x, max_x = domain.get_mesh_bounding_box()[:,0] eps = 1e-8 * (max_x - min_x) omega = domain.create_region('Omega', 'all') gamma1 = domain.create_region('Gamma1', 'vertices in x < %.10f' % (min_x + eps), 'facet') gamma2 = domain.create_region('Gamma2', 'vertices in x > %.10f' % (max_x - eps), 'facet') field = Field.from_args('fu', nm.float64, 'vector', omega, approx_order=2) u = FieldVariable('u', 'unknown', field) v = FieldVariable('v', 'test', field, primary_var_name='u') m = Material('m', D=stiffness_from_lame(dim=2, lam=1.0, mu=1.0)) f = Material('f', val=[[0.02], [0.01]]) integral = Integral('i', order=3) t1 = Term.new('dw_lin_elastic(m.D, v, u)', integral, omega, m=m, v=v, u=u) t2 = Term.new('dw_volume_lvf(f.val, v)', integral, omega, f=f, v=v) eq = Equation('balance', t1 + t2) eqs = Equations([eq]) fix_u = EssentialBC('fix_u', gamma1, {'u.all' : 0.0}) bc_fun = Function('shift_u_fun', shift_u_fun, extra_args={'shift' : 0.01}) shift_u = EssentialBC('shift_u', gamma2, {'u.0' : bc_fun}) ls = ScipyDirect({}) nls_status = IndexedStruct() nls = Newton({}, lin_solver=ls, status=nls_status) pb = Problem('elasticity', equations=eqs) pb.save_regions_as_groups('regions') pb.set_bcs(ebcs=Conditions([fix_u, shift_u])) pb.set_solver(nls) status = IndexedStruct() state = pb.solve(status=status) print('Nonlinear solver status:\n', nls_status) print('Stationary solver status:\n', status) pb.save_state('linear_elasticity.vtk', state) if options.show: view = Viewer('linear_elasticity.vtk') view(vector_mode='warp_norm', rel_scaling=2, is_scalar_bar=True, is_wireframe=True)