示例#1
0
    def __init__(self, V, options=None):
        # See if we have dofmap
        if not is_function_space(V):
            raise ValueError("V is not a function space.")

        # Only allow 2d and 3d meshes
        if V.mesh().geometry().dim() == 1:
            raise ValueError("Only 2d and 3d meshes are supported.")

        # Get MPI info
        try:
            from dolfin import mpi_comm_world

            self.mpi_size = MPI.size(mpi_comm_world())
            self.mpi_rank = MPI.rank(mpi_comm_world())
        except ImportError:
            self.mpi_size = MPI.num_processes()
            self.mpi_rank = MPI.process_number()

        # Analyze the space V
        self.V = V
        self.dofmaps = extract_dofmaps(self.V)
        self.bounds = bounds(self.V)

        # Rewrite default plotting options if they are provided by user
        self.options = {"colors": {"mesh_entities": "hsv", "mesh": "Blues"}, "xkcd": False, "markersize": 40}
        if options is not None:
            self.options.update(options)

        # Keep track of the plots
        self.plots = []
示例#2
0
def save_results(problem, solver, num_dofs, mesh_size, time_step, functional,
                 error):
    'Save results to file.'
    # Print summary
    if MPI.process_number() == 0:
        print ''
        print 'Problem    |', problem
        print 'Solver     |', solver
        print 'Unknowns   |', num_dofs
        print 'Mesh size  |', mesh_size
        print 'Time step  |', time_step
        print 'Functional |', functional
        print 'Error      |', error

        # Print DOLFIN summary
        set_log_active(True)
        list_timings()

        # Append to file, let each dx, dt have its own log file
        results_dir = problem.options['results_dir']
        dx = problem.options['refinement_level']
        dt = problem.options['dt_division']

        name = '%s_%s_results_dx%d_dt%d.log' % (str(problem), str(solver), dx,
                                                dt)
        filename = os.path.join(results_dir, name)

        # create the dir for results if needed
        if not os.path.exists(os.path.dirname(filename)):
            os.makedirs(os.path.dirname(filename))

        with open(filename, 'a') as f:
            f.write('%s, %s, %s, %d, %.15g, %.15g, %.15g, %s\n' %
                    (time.asctime(), problem, solver, num_dofs, mesh_size,
                     time_step, functional, str(error)))
示例#3
0
def save_results(problem, solver, num_dofs, mesh_size, time_step, functional, error):
  'Save results to file.'
  # Print summary
  if MPI.process_number() == 0 :
    print ''
    print 'Problem    |', problem
    print 'Solver     |', solver
    print 'Unknowns   |', num_dofs
    print 'Mesh size  |', mesh_size
    print 'Time step  |', time_step
    print 'Functional |', functional
    print 'Error      |', error

    # Print DOLFIN summary
    set_log_active(True)
    list_timings()

    # Append to file, let each dx, dt have its own log file
    results_dir = problem.options['results_dir']
    dx = problem.options['refinement_level']
    dt = problem.options['dt_division']

    name = '%s_%s_results_dx%d_dt%d.log' % (str(problem), str(solver), dx, dt)
    filename = os.path.join(results_dir, name)

    # create the dir for results if needed
    if not os.path.exists(os.path.dirname(filename)):
      os.makedirs(os.path.dirname(filename))

    with open(filename, 'a') as f:
      f.write('%s, %s, %s, %d, %.15g, %.15g, %.15g, %s\n' %
             (time.asctime(), problem, solver, num_dofs, mesh_size, time_step, functional, str(error)))
示例#4
0
def solve(solver_name, problem_name, options):
    'Solve the problem by solver with options.'

    # Set cpp_compiler options
    parameters["form_compiler"]["cpp_optimize"] = True

    # Set debug level
    set_log_active(options['debug'])

    # Set refinement level
    options['N'] = mesh_sizes[options['refinement_level']]

    # Create problem and solver
    problem = Problem(problem_name, options)
    solver = Solver(solver_name, options)

    time_step = solver.get_timestep(problem)[0]

    if MPI.process_number() == 0 and options['verbose']:
        print 'Problem: ' + str(problem)
        print 'Solver:  ' + str(solver)

    # Solve problem with solver
    wct = time.time()
    u, p = solver.solve(problem)

    # Compute elapsed time
    wct = time.time() - wct

    # Compute number of degrees of freedom
    num_dofs = u.vector().size() + p.vector().size()

    # Get the mesh size
    mesh_size = u.function_space().mesh().hmin()

    # Get functional value and error
    functional, error = solver.eval()

    # Save results
    cpu_time = solver.cputime()
    save_results(problem, solver, num_dofs, mesh_size, time_step, functional,
                 error)

    return 0
示例#5
0
def solve(solver_name, problem_name, options):
  'Solve the problem by solver with options.'

  # Set cpp_compiler options
  parameters["form_compiler"]["cpp_optimize"] = True

  # Set debug level
  set_log_active(options['debug'])

  # Set refinement level
  options['N'] = mesh_sizes[options['refinement_level']]

  # Create problem and solver
  problem = Problem(problem_name, options)
  solver = Solver(solver_name, options)

  time_step = solver.get_timestep(problem)[0]

  if MPI.process_number() == 0 and options['verbose']:
    print 'Problem: ' + str(problem)
    print 'Solver:  ' + str(solver)

  # Solve problem with solver
  wct = time.time()
  u, p = solver.solve(problem)

  # Compute elapsed time
  wct = time.time() - wct

  # Compute number of degrees of freedom
  num_dofs = u.vector().size() + p.vector().size()

  # Get the mesh size
  mesh_size = u.function_space().mesh().hmin()

  # Get functional value and error
  functional, error = solver.eval()

  # Save results
  cpu_time = solver.cputime()
  save_results(problem, solver, num_dofs, mesh_size, time_step, functional, error)

  return 0
示例#6
0
def save_convergence_plot(errors, element_sizes, title, legend, order, offset = 0.8, show_title = True, xlabel = 'Element size [m]', ylabel = r"$\mathcal E$ error"):
    ''' Creates a convergence plot '''
    if MPI.process_number() != 0:
        return

    # Plot the errors
    scaling = 0.7
    rc('text', usetex=True)
    plt.figure(1, figsize=(scaling*7,scaling*4))

    plt.xlabel('Element size')
    plt.ylabel('Error')
    if show_title:
        plt.title(title)

    plt.loglog(element_sizes, errors, 'gx', label = legend, color = 'k')
    # Construct an error plot with the expected order
    c = errors[-1]/element_sizes[-1]**order*offset
    expected_errors = [c*element_size**order for element_size in element_sizes] 
    print order
    if order == 1.0:
        order_str = "First order"
    elif order == 2.0:
        order_str = "Second order"
    else:
        order_str = str(order) + " order"
    plt.loglog(element_sizes, expected_errors, label = order_str, color = 'k')

    plt.legend(loc=4)
    #plt.axis([min(element_sizes)*1.01, max(element_sizes)*1.01, min(errors)*1.01, max(errors)*1.01])
    plt.gcf().subplots_adjust(bottom=0.15)
    plt.xlabel(xlabel)
    plt.ylabel(ylabel)

    filename = '_'.join(title.split()).lower()
    print 'Saving as: ', filename 
    plt.savefig(filename + '.png')
    plt.savefig(filename + '.pdf')
    plt.close()
示例#7
0
    def __init__(self, V, options=None):
        # See if we have dofmap
        if not is_function_space(V):
            raise ValueError('V is not a function space.')

        # Only allow 2d and 3d meshes
        if V.mesh().geometry().dim() == 1:
            raise ValueError('Only 2d and 3d meshes are supported.')

        # Get MPI info
        try:
            from dolfin import mpi_comm_world
            self.mpi_size = MPI.size(mpi_comm_world())
            self.mpi_rank = MPI.rank(mpi_comm_world())
        except ImportError:
            self.mpi_size = MPI.num_processes()
            self.mpi_rank = MPI.process_number()

        # Analyze the space V
        self.V = V
        self.dofmaps = extract_dofmaps(self.V)
        self.elements = extract_elements(self.V)
        self.bounds = bounds(self.V)

        # Rewrite default plotting options if they are provided by user
        self.options = {
            'colors': {
                'mesh_entities': 'hsv',
                'mesh': 'Blues'
            },
            'xkcd': False,
            'markersize': 40
        }
        if options is not None:
            self.options.update(options)

        # Keep track of the plots
        self.plots = []
示例#8
0
def main(args):
    'Parse command-line arguments and run solver'

    # Check arguments
    if not len(args) >= 2:
        usage()
        return 2

    # Get problem and solver
    problem_name, solver_name = args[:2]

    # Get options
    options = OPTIONS.copy()
    for arg in args[2:]:
        try:
            key, value = arg.split('=')
            try:
                options[key] = eval(value)
            except:
                options[key] = str(value)
        except:
            print 'Warning: Unhandled command-line argument', arg

    # Parse the spatial and time stepping options.
    # If either refinement_level or dt_division are lists feed the items of
    # list one by one
    type_dx = type(options['refinement_level'])
    type_dt = type(options['dt_division'])

    if type_dx is list:
        if type_dt is int:
            # Do a dx convergence study
            if MPI.process_number() == 0:
                print_color(
                    'Dx convergence study, dt=%d' % options['dt_division'],
                    'cyan')
            refinement_levels = copy.copy(options['refinement_level'])

            # loop over dx
            for refinement_level in refinement_levels:
                if MPI.process_number() == 0:
                    print_color('\tRefinement level %d' % refinement_level,
                                'yellow')
                options['refinement_level'] = refinement_level
                # solve with fixed dt and changing dx

                # Warn user about running dx convergence with changing dt, this happens
                # if problem has no dt
                _options = options.copy()
                _options['N'] = mesh_sizes[_options['refinement_level']]
                _problem = Problem(problem_name, _options)

                if _problem.dt is None:
                    print_color(
                        '        Warning: Dx convergence study with changing dt',
                        'pink')

                solve(solver_name, problem_name, options)

        else:
            raise ValueError(
                'Use fixed dt_division with changing refinement_level!')

    elif type_dx is int:
        if type_dt is list:
            # Do a dt convergence study
            if MPI.process_number() == 0:
                print_color(
                    'Dt convergence study, dx=%d' %
                    options['refinement_level'], 'cyan')
            dt_divisions = copy.copy(options['dt_division'])

            # loop over dt
            for dt_division in dt_divisions:
                if MPI.process_number() == 0:
                    print_color('\tDt division %d' % dt_division, 'yellow')
                options['dt_division'] = dt_division
                #solve with fixed dx and changing dt
                solve(solver_name, problem_name, options)

        elif type(options['dt_division']) is int:
            if MPI.process_number() == 0:
                print_color('Fixed dx and dt', 'cyan')
            # solve with fixed dx and fixed dt
            solve(solver_name, problem_name, options)

        else:
            raise ValueError("options['dt_division'] must be int of list!")
    else:
        raise ValueError("options['refinement_level'] must be int of list!")

    return 0
示例#9
0
def main(args):
  'Parse command-line arguments and run solver'

  # Check arguments
  if not len(args) >= 2:
    usage()
    return 2

  # Get problem and solver
  problem_name, solver_name = args[:2]

  # Get options
  options = OPTIONS.copy()
  for arg in args[2:]:
    try:
      key, value = arg.split('=')
      try:
        options[key] = eval(value)
      except:
        options[key] = str(value)
    except:
      print 'Warning: Unhandled command-line argument', arg

  # Parse the spatial and time stepping options.
  # If either refinement_level or dt_division are lists feed the items of
  # list one by one
  type_dx = type(options['refinement_level'])
  type_dt = type(options['dt_division'])

  if type_dx is list:
    if type_dt is int:
      # Do a dx convergence study
      if MPI.process_number() == 0:
        print_color('Dx convergence study, dt=%d' % options['dt_division'], 'cyan')
      refinement_levels = copy.copy(options['refinement_level'])

      # loop over dx
      for refinement_level in refinement_levels:
        if MPI.process_number() == 0:
          print_color('\tRefinement level %d' % refinement_level, 'yellow')
        options['refinement_level'] = refinement_level
        # solve with fixed dt and changing dx

        # Warn user about running dx convergence with changing dt, this happens
        # if problem has no dt
        _options = options.copy()
        _options['N'] = mesh_sizes[_options['refinement_level']]
        _problem = Problem(problem_name, _options)

        if _problem.dt is None:
          print_color('        Warning: Dx convergence study with changing dt', 'pink')

        solve(solver_name, problem_name, options)

    else:
      raise ValueError('Use fixed dt_division with changing refinement_level!')

  elif type_dx is int:
    if type_dt is list:
      # Do a dt convergence study
      if MPI.process_number() == 0:
        print_color('Dt convergence study, dx=%d' % options['refinement_level'],'cyan')
      dt_divisions = copy.copy(options['dt_division'])

      # loop over dt
      for dt_division in dt_divisions:
        if MPI.process_number() == 0:
          print_color('\tDt division %d' % dt_division, 'yellow')
        options['dt_division'] = dt_division
        #solve with fixed dx and changing dt
        solve(solver_name, problem_name, options)

    elif type(options['dt_division']) is int:
      if MPI.process_number() == 0:
        print_color('Fixed dx and dt', 'cyan')
      # solve with fixed dx and fixed dt
      solve(solver_name, problem_name, options)

    else:
      raise ValueError("options['dt_division'] must be int of list!")
  else:
      raise ValueError("options['refinement_level'] must be int of list!")

  return 0