Example #1
0
int main(int argc, char **args)
{
  // Test variable.
  int success_test = 1;

	if (argc < 2) error("Not enough parameters.");

  // Load the mesh.
	Mesh mesh;
  H3DReader mloader;
  if (!mloader.load(args[1], &mesh)) error("Loading mesh file '%s'.", args[1]);

  // Initialize the space 1.
	Ord3 o1(2, 2, 2);
	H1Space space1(&mesh, bc_types, essential_bc_values_1, o1);

	// Initialize the space 2.
	Ord3 o2(4, 4, 4);
	H1Space space2(&mesh, bc_types, essential_bc_values_2, o2);

  // Initialize the weak formulation.
	WeakForm wf(2);
	wf.add_matrix_form(0, 0, bilinear_form_1<double, scalar>, bilinear_form_1<Ord, Ord>, HERMES_SYM);
	wf.add_vector_form(0, linear_form_1<double, scalar>, linear_form_1<Ord, Ord>);
	wf.add_matrix_form(1, 1, bilinear_form_2<double, scalar>, bilinear_form_2<Ord, Ord>, HERMES_SYM);
	wf.add_vector_form(1, linear_form_2<double, scalar>, linear_form_2<Ord, Ord>);

  // Initialize the FE problem.
  bool is_linear = true;
  DiscreteProblem dp(&wf, Hermes::vector<Space *>(&space1, &space2), is_linear);

  // Set up the solver, matrix, and rhs according to the solver selection.
  SparseMatrix* matrix = create_matrix(matrix_solver);
  Vector* rhs = create_vector(matrix_solver);
  Solver* solver = create_linear_solver(matrix_solver, matrix, rhs);

  // Initialize the preconditioner in the case of SOLVER_AZTECOO.
  if (matrix_solver == SOLVER_AZTECOO) 
  {
    ((AztecOOSolver*) solver)->set_solver(iterative_method);
    ((AztecOOSolver*) solver)->set_precond(preconditioner);
    // Using default iteration parameters (see solver/aztecoo.h).
  }

  // Assemble the linear problem.
  info("Assembling (ndof: %d).", Space::get_num_dofs(Hermes::vector<Space *>(&space1, &space2)));
  dp.assemble(matrix, rhs);

  // Solve the linear system. If successful, obtain the solution.
  info("Solving.");
		Solution sln1(&mesh);
		Solution sln2(&mesh);
  if(solver->solve()) Solution::vector_to_solutions(solver->get_solution(), Hermes::vector<Space *>(&space1, &space2), Hermes::vector<Solution *>(&sln1, &sln2));
  else error ("Matrix solver failed.\n");

  ExactSolution ex_sln1(&mesh, exact_sln_fn_1);
  ExactSolution ex_sln2(&mesh, exact_sln_fn_2);

  // Calculate exact error.
  info("Calculating exact error.");
  Adapt *adaptivity = new Adapt(Hermes::vector<Space *>(&space1, &space2), Hermes::vector<ProjNormType>(HERMES_H1_NORM, HERMES_H1_NORM));
  bool solutions_for_adapt = false;
  double err_exact = adaptivity->calc_err_exact(Hermes::vector<Solution *>(&sln1, &sln2), Hermes::vector<Solution *>(&ex_sln1, &ex_sln2), solutions_for_adapt, HERMES_TOTAL_ERROR_ABS);

  if (err_exact > EPS)
		// Calculated solution is not precise enough.
		success_test = 0;

  // Clean up.
  delete matrix;
  delete rhs;
  delete solver;
  delete adaptivity;
  
  if (success_test) {
    info("Success!");
    return ERR_SUCCESS;
	}
	else {
    info("Failure!");
    return ERR_FAILURE;
	}
}
Example #2
0
int main(int argc, char* argv[])
{
  // Time measurement.
  TimePeriod cpu_time;

  // Load the mesh.
  info("Loading mesh...");
  Mesh mesh;
  H3DReader mloader;
  cpu_time.reset();
  mloader.load("mol.mesh3d", &mesh);
  cpu_time.tick();
  info("Time taken for loading mesh : %g s", cpu_time.accumulated());
  cpu_time.reset();

  // Perform initial mesh refinements.
  for (int i = 0; i < INIT_REF_NUM; i++) mesh.refine_all_elements(H3D_H3D_H3D_REFT_HEX_XYZ);
  int NUM_ELEMS = mesh.get_max_element_id();
  info("NUM_ELEMS = %d", NUM_ELEMS);
  cpu_time.tick();
  info("Time for refining mesh: %g s", cpu_time.accumulated());
  cpu_time.reset();

  // Setting up space for eigen value calculation with zero boundary conditions.
  H1Space space(&mesh, bc_types, essential_bc_values_eigen, Ord3(P_INIT_X, P_INIT_Y, P_INIT_Z));

  // Setting up space for solution of  Poisson equation with (approximate) boundary conditions 2*N/sqrt(x*x+y*y+z*z).
  H1Space space_poisson(&mesh, bc_types, essential_bc_values_poisson, Ord3(P_INIT_X, P_INIT_Y, P_INIT_Z));
  bool is_linear = true;

  // Setting up Laplace matrix for solving the Poisson equation. 
  WeakForm wf_poisson;
  wf_poisson.add_matrix_form(bilinear_form_laplace, bilinear_form_ord1, HERMES_SYM, HERMES_ANY_INT);
  RCP<SparseMatrix> matrix_Laplace = rcp(new CSCMatrix());
  Solver* solver = create_linear_solver(matrix_solver, matrix_Laplace.get());
  DiscreteProblem dp_poisson(&wf_poisson, &space, is_linear);
  dp_poisson.assemble(matrix_Laplace.get());
  int ndof = Space::get_num_dofs(&space);
  info("ndof = %d", ndof);
  ExactSolution pot_exact(&mesh, pot);
  ExactSolution wfun_exact(&mesh, wfun);
  Solution coul_pot(space.get_mesh());
  coul_pot.set_zero();                 // coul_pot zero at the beginning.

  // Initialize the weak formulation for the left hand side, i.e., H.
  info("Initializing weak form...");
  WeakForm wf_left, wf_right;
  wf_left.add_matrix_form(bilinear_form_left, bilinear_form_ord, HERMES_SYM, HERMES_ANY_INT,
                          Hermes::vector<MeshFunction*>(&pot_exact, &wfun_exact,&coul_pot ));
  wf_right.add_matrix_form(bilinear_form_right, bilinear_form_ord, HERMES_SYM, HERMES_ANY_INT, &wfun_exact);   
  DiscreteProblem dp(&wf_left, &space, is_linear);

  // Initialize matrices and matrix solver.
  RCP<SparseMatrix> matrix_left = rcp(new CSCMatrix());
  RCP<SparseMatrix> matrix_right = rcp(new CSCMatrix());
  cpu_time.reset();
  info("Assembling RHS matrix....");
  DiscreteProblem dp_left(&wf_left, &space, is_linear);
  DiscreteProblem dp_right(&wf_right, &space, is_linear);
  dp_right.assemble(matrix_right.get());
  cpu_time.tick();
  info("time taken to assemble RHS matrix: %g s", cpu_time.accumulated());
  WeakForm wf_coulomb;
  wf_coulomb.add_matrix_form(bilinear_form_coul_pot, bilinear_form_ord1, HERMES_SYM, HERMES_ANY_INT,
                             Hermes::vector<MeshFunction*>(&wfun_exact,&coul_pot ));
  RCP<SparseMatrix> matrix_coulomb = rcp(new CSCMatrix());
  DiscreteProblem dp_coulomb(&wf_coulomb, &space, is_linear);
  Solution sln(space.get_mesh());
  RCP<SparseMatrix> matrix_U = rcp(new CSCMatrix());
  bool DONE=false;
  int iter=0;
  info("SELF CONSISTENT LOOP BEGINS:");
  fflush(stdout);

  // Now follows the self consistent loop:
  while (!DONE){
    WeakForm  wf;
    Vector* rhs=create_vector(matrix_solver);
    Solver* solver = create_linear_solver(matrix_solver, matrix_left.get());
    dp_left.assemble(matrix_left.get());
    cpu_time.tick();
    info("time taken for assembling LHS matrix : %g", cpu_time.accumulated());
    cpu_time.reset();
    dp_coulomb.assemble(matrix_coulomb.get());
    cpu_time.tick();
    info("time for assembling  matrix_coulomb: %g  " , cpu_time.accumulated());

    // Initialize eigensolver.
    cpu_time.reset();
    EigenSolver es(matrix_left, matrix_right);
    cpu_time.tick();
    info("Total running time for preparing generalized eigenvalue problem: %g s\n", cpu_time.accumulated());

    cpu_time.reset();
    info("Using eigensolver...");
    es.solve(NUMBER_OF_EIGENVALUES, TARGET_VALUE, TOL, MAX_ITER);
    info("Total running time for solving generalized eigenvalue problem: %g s", cpu_time.accumulated());
    double* coeff_vec;
    double coulomb_energy;
    int neig = es.get_n_eigs();
    double *eival = new double[neig]; 
    if (neig != NUMBER_OF_EIGENVALUES) error("Mismatched number of eigenvectors in eigensolver");  
    for (int ieig = 0; ieig < neig; ieig++) {
      int n;
      es.get_eigenvector(ieig, &coeff_vec, &n);

      // Convert coefficient vector into a Solution.
      Solution::vector_to_solution(coeff_vec, &space, &sln);
      double norm2=expectation_value(coeff_vec, matrix_right.get(),ndof);
      coulomb_energy=expectation_value(coeff_vec,matrix_coulomb.get(),ndof);
      eival[ieig]=es.get_eigenvalue(ieig);
      info("eigenvector %d : norm=%25.16f \n eigenvalue=%25.16f \n coulomb_energy=%25.16f ",
           ieig, pow(norm2, 0.5), eival[ieig], coulomb_energy);
      wf.add_vector_form(linear_form_poisson, linear_form_poisson_ord, HERMES_ANY_INT,
                         Hermes::vector<MeshFunction*>(&sln, &wfun_exact)); 
      out_fn_vtk(&sln, "phi", ieig);
    }  
    double HFenergy = 2*eival[0] - coulomb_energy;
    info("HF energy for two electrons=%25.16f", HFenergy);
    DiscreteProblem dp_density(&wf, &space, is_linear);
    dp_density.assemble(matrix_U.get(), rhs);
    Solver* solver_poisson = create_linear_solver(matrix_solver, matrix_Laplace.get(),rhs);
    info("Solving the matrix problem.");
    fflush(stdout);
    if(solver_poisson->solve())
	Solution::vector_to_solution(solver_poisson->get_solution(), &space_poisson, &coul_pot);
    else
      error ("Matrix solver failed.\n");
    out_fn_vtk(&coul_pot, "coul_pot", 0);
    iter++; 
    if (iter > MAX_SCF_ITER){ 
      delete [] coeff_vec;
      DONE=true;    
    } 
  }

  // missing mesh file mol.mesh3d, supposed to fail temporary.
  return ERR_FAILURE;
};
Example #3
0
int main(int argc, char **args) 
{
  // Test variable.
  int success_test = 1;

  if (argc < 3) error("Not enough parameters.");

  if (strcmp(args[1], "h1") != 0 && strcmp(args[1], "h1-ipol"))
    error("Unknown type of the projection.");

	// Load the mesh.
  Mesh mesh;
  H3DReader mloader;
  if (!mloader.load(args[2], &mesh)) error("Loading mesh file '%s'.", args[1]);

	// Refine the mesh.
  mesh.refine_all_elements(H3D_H3D_H3D_REFT_HEX_XYZ);

	// Initialize the space.
#if defined X2_Y2_Z2
  Ord3 order(2, 2, 2);
#elif defined X3_Y3_Z3
  Ord3 order(3, 3, 3);
#elif defined XN_YM_ZO
  Ord3 order(2, 3, 4);
#endif
  H1Space space(&mesh, bc_types, essential_bc_values, order);

  // Initialize the weak formulation.
  WeakForm wf;
  wf.add_matrix_form(bilinear_form<double, scalar>, bilinear_form<Ord, Ord>, HERMES_SYM, HERMES_ANY);
  wf.add_vector_form(linear_form<double, scalar>, linear_form<Ord, Ord>, HERMES_ANY);

  // Initialize the FE problem.
  bool is_linear = true;
  DiscreteProblem dp(&wf, &space, is_linear);

  // Set up the solver, matrix, and rhs according to the solver selection.
  SparseMatrix* matrix = create_matrix(matrix_solver);
  Vector* rhs = create_vector(matrix_solver);
  Solver* solver = create_linear_solver(matrix_solver, matrix, rhs);

  // Initialize the preconditioner in the case of SOLVER_AZTECOO.
  if (matrix_solver == SOLVER_AZTECOO) 
  {
    ((AztecOOSolver*) solver)->set_solver(iterative_method);
    ((AztecOOSolver*) solver)->set_precond(preconditioner);
    // Using default iteration parameters (see solver/aztecoo.h).
  }

  // Assemble the linear problem.
  dp.assemble(matrix, rhs);

  // Solve the linear system. If successful, obtain the solution.
  info("Solving the linear problem.");
  Solution sln(&mesh);
  if(solver->solve()) Solution::vector_to_solution(solver->get_solution(), &space, &sln);
  else {
	  info("Matrix solver failed.");
	  success_test = 0;
  }

  unsigned int ne = mesh.get_num_base_elements();
  for (unsigned int idx = mesh.elements.first(); idx <= ne; idx = mesh.elements.next(idx)) {
    Element *e = mesh.elements[idx];

    Ord3 order(4, 4, 4);
    double error;

    Projection *proj;
    if (strcmp(args[1], "h1") == 0) proj = new H1Projection(&sln, e, space.get_shapeset());
    else if (strcmp(args[1], "h1-ipol") == 0) proj = new H1ProjectionIpol(&sln, e, space.get_shapeset());
    else success_test = 0;

    error = 0.0;
    error += proj->get_error(H3D_REFT_HEX_NONE, -1, order);
    error = sqrt(error);
    
    if (error > EPS)
		    // Calculated solution is not precise enough.
		    success_test = 0;

    //
    error = 0.0;
    error += proj->get_error(H3D_REFT_HEX_X, 20, order);
    error += proj->get_error(H3D_REFT_HEX_X, 21, order);
    error = sqrt(error);
    if (error > EPS)
		    // Calculated solution is not precise enough.
		    success_test = 0;

    //
    error = 0.0;
    error += proj->get_error(H3D_REFT_HEX_Y, 22, order);
    error += proj->get_error(H3D_REFT_HEX_Y, 23, order);
    error = sqrt(error);
    if (error > EPS)
		    // Calculated solution is not precise enough.
		    success_test = 0;

    //
    error = 0.0;
    error += proj->get_error(H3D_REFT_HEX_Z, 24, order);
    error += proj->get_error(H3D_REFT_HEX_Z, 25, order);
    error = sqrt(error);
    if (error > EPS)
		    // Calculated solution is not precise enough.
		    success_test = 0;

    //
    error = 0.0;
    error += proj->get_error(H3D_H3D_REFT_HEX_XY,  8, order);
    error += proj->get_error(H3D_H3D_REFT_HEX_XY,  9, order);
    error += proj->get_error(H3D_H3D_REFT_HEX_XY, 10, order);
    error += proj->get_error(H3D_H3D_REFT_HEX_XY, 11, order);
    error = sqrt(error);
    if (error > EPS)
		    // Calculated solution is not precise enough.
		    success_test = 0;

    //
    error = 0.0;
    error += proj->get_error(H3D_H3D_REFT_HEX_XZ, 12, order);
    error += proj->get_error(H3D_H3D_REFT_HEX_XZ, 13, order);
    error += proj->get_error(H3D_H3D_REFT_HEX_XZ, 14, order);
    error += proj->get_error(H3D_H3D_REFT_HEX_XZ, 15, order);
    error = sqrt(error);
    if (error > EPS)
		    // Calculated solution is not precise enough.
		    success_test = 0;

    //
    error = 0.0;
    error += proj->get_error(H3D_H3D_REFT_HEX_YZ, 16, order);
    error += proj->get_error(H3D_H3D_REFT_HEX_YZ, 17, order);
    error += proj->get_error(H3D_H3D_REFT_HEX_YZ, 18, order);
    error += proj->get_error(H3D_H3D_REFT_HEX_YZ, 19, order);
    error = sqrt(error);
    if (error > EPS)
		    // Calculated solution is not precise enough.
		    success_test = 0;

    //
    error = 0.0;
    for (int j = 0; j < 8; j++)
      error += proj->get_error(H3D_H3D_H3D_REFT_HEX_XYZ, j, order);
    error = sqrt(error);

    delete proj;
    
    if (error > EPS)
		    // Calculated solution is not precise enough.
		    success_test = 0;
  }

  if (success_test) {
    info("Success!");
    return ERR_SUCCESS;
  }
  else {
    info("Failure!");
    return ERR_FAILURE;
  }
}
Example #4
0
int main(int argc, char **args)
{
  // Test variable.
  int success_test = 1;

	if (argc < 5) error("Not enough parameters.");

  // Load the mesh.
	Mesh mesh;
	H3DReader mloader;
	if (!mloader.load(args[1], &mesh)) error("Loading mesh file '%s'.", args[1]);

  // Initialize the space according to the
  // command-line parameters passed.
  sscanf(args[2], "%d", &m);
	sscanf(args[3], "%d", &n);
	sscanf(args[4], "%d", &o);
	int mx = maxn(4, m, n, o, 4);
	Ord3 order(mx, mx, mx);
	H1Space space(&mesh, bc_types, NULL, order);

  // Initialize the weak formulation.
  WeakForm wf;
  wf.add_matrix_form(bilinear_form<double, scalar>, bilinear_form<Ord, Ord>, HERMES_SYM);
  wf.add_vector_form(linear_form<double, scalar>, linear_form<Ord, Ord>);
  wf.add_vector_form_surf(linear_form_surf<double, scalar>, linear_form_surf<Ord, Ord>);

  // Initialize the FE problem.
  bool is_linear = true;
  DiscreteProblem dp(&wf, &space, is_linear);

  // Initialize the solver in the case of SOLVER_PETSC or SOLVER_MUMPS.
  initialize_solution_environment(matrix_solver, argc, args);

  // Set up the solver, matrix, and rhs according to the solver selection.
  SparseMatrix* matrix = create_matrix(matrix_solver);
  Vector* rhs = create_vector(matrix_solver);
  Solver* solver = create_linear_solver(matrix_solver, matrix, rhs);

  // Initialize the preconditioner in the case of SOLVER_AZTECOO.
  if (matrix_solver == SOLVER_AZTECOO) 
  {
    ((AztecOOSolver*) solver)->set_solver(iterative_method);
    ((AztecOOSolver*) solver)->set_precond(preconditioner);
    // Using default iteration parameters (see solver/aztecoo.h).
  }

  // Assemble the linear problem.
  info("Assembling (ndof: %d).", Space::get_num_dofs(&space));
  dp.assemble(matrix, rhs);
    
  // Solve the linear system. If successful, obtain the solution.
  info("Solving.");
  Solution sln(&mesh);
  if(solver->solve()) Solution::vector_to_solution(solver->get_solution(), &space, &sln);
  else error ("Matrix solver failed.\n");

  ExactSolution ex_sln(&mesh, exact_solution);

  // Calculate exact error.
  info("Calculating exact error.");
  Adapt *adaptivity = new Adapt(&space, HERMES_H1_NORM);
  bool solutions_for_adapt = false;
  double err_exact = adaptivity->calc_err_exact(&sln, &ex_sln, solutions_for_adapt, HERMES_TOTAL_ERROR_ABS);

  if (err_exact > EPS)
		// Calculated solution is not precise enough.
		success_test = 0;

  // Clean up.
  delete matrix;
  delete rhs;
  delete solver;
  delete adaptivity;

  // Properly terminate the solver in the case of SOLVER_PETSC or SOLVER_MUMPS.
  finalize_solution_environment(matrix_solver);
  
  if (success_test) {
    info("Success!");
    return ERR_SUCCESS;
	}
	else {
    info("Failure!");
    return ERR_FAILURE;
	}
}
Example #5
0
int main(int argc, char **args)
{
  // Test variable.
  int success_test = 1;

  if (argc < 2) error("Not enough parameters.");

  // Load the mesh.
	Mesh mesh;
  H3DReader mloader;
  if (!mloader.load(args[1], &mesh)) error("Loading mesh file '%s'.", args[1]);

	// Initialize the space.
#if defined NONLIN1
	Ord3 order(1, 1, 1);
#else
	Ord3 order(2, 2, 2);
#endif
	H1Space space(&mesh, bc_types, essential_bc_values, order);

#if defined NONLIN2
	// Do L2 projection of zero function.
	WeakForm proj_wf;
	proj_wf.add_matrix_form(biproj_form<double, scalar>, biproj_form<Ord, Ord>, HERMES_SYM);
	proj_wf.add_vector_form(liproj_form<double, scalar>, liproj_form<Ord, Ord>);

	bool is_linear = true;
	DiscreteProblem lp(&proj_wf, &space, is_linear);

	// Initialize the solver in the case of SOLVER_PETSC or SOLVER_MUMPS.
  initialize_solution_environment(matrix_solver, argc, args);

  // Set up the solver, matrix, and rhs according to the solver selection.
  SparseMatrix* matrix = create_matrix(matrix_solver);
  Vector* rhs = create_vector(matrix_solver);
  Solver* solver_proj = create_linear_solver(matrix_solver, matrix, rhs);
  
  // Initialize the preconditioner in the case of SOLVER_AZTECOO.
  if (matrix_solver == SOLVER_AZTECOO) 
  {
    ((AztecOOSolver*) solver_proj)->set_solver(iterative_method);
    ((AztecOOSolver*) solver_proj)->set_precond(preconditioner);
    // Using default iteration parameters (see solver/aztecoo.h).
  }
  
  // Assemble the linear problem.
  info("Assembling (ndof: %d).", Space::get_num_dofs(&space));
  lp.assemble(matrix, rhs);
    
  // Solve the linear system.
  info("Solving.");
  if(!solver_proj->solve());
  	error ("Matrix solver failed.\n");

  delete matrix;
  delete rhs;
#endif

	// Initialize the weak formulation.
	WeakForm wf(1);
	wf.add_matrix_form(0, 0, jacobi_form<double, scalar>, jacobi_form<Ord, Ord>, HERMES_UNSYM);
	wf.add_vector_form(0, resid_form<double, scalar>, resid_form<Ord, Ord>);

	// Initialize the FE problem.
#if defined NONLIN2
  is_linear = false;
#else
  bool is_linear = false;
#endif
	DiscreteProblem dp(&wf, &space, is_linear);

	NoxSolver solver(&dp);

#if defined NONLIN2
solver.set_init_sln(solver_proj->get_solution());
delete solver_proj;
#endif

solver.set_conv_iters(10);
	info("Solving.");
	Solution sln(&mesh);
	if(solver.solve()) Solution::vector_to_solution(solver.get_solution(), &space, &sln);
  else error ("Matrix solver failed.\n");

		Solution ex_sln(&mesh);
#ifdef NONLIN1
		ex_sln.set_const(100.0);
#else
		ex_sln.set_exact(exact_solution);
#endif
		// Calculate exact error.
  info("Calculating exact error.");
  Adapt *adaptivity = new Adapt(&space, HERMES_H1_NORM);
  bool solutions_for_adapt = false;
  double err_exact = adaptivity->calc_err_exact(&sln, &ex_sln, solutions_for_adapt, HERMES_TOTAL_ERROR_ABS);

  if (err_exact > EPS)
		// Calculated solution is not precise enough.
		success_test = 0;

  if (success_test) {
    info("Success!");
    return ERR_SUCCESS;
  }
  else {
    info("Failure!");
    return ERR_FAILURE;
  }
}
Example #6
0
int main(int argc, char **args) 
{
  // Test variable.
  int success_test = 1;

  if (argc < 2) error("Not enough parameters.");

  // Load the mesh.
	Mesh mesh;
  H3DReader mloader;
  if (!mloader.load(args[1], &mesh)) error("Loading mesh file '%s'.", args[1]);

	// Initialize the space.
	int mx = 2;
	Ord3 order(mx, mx, mx);
	H1Space space(&mesh, bc_types, NULL, order);
#if defined LIN_DIRICHLET || defined NLN_DIRICHLET
	space.set_essential_bc_values(essential_bc_values);
#endif
	// Initialize the weak formulation.
	WeakForm wf;
	wf.add_vector_form(form_0<double, scalar>, form_0<Ord, Ord>);
#if defined LIN_NEUMANN || defined LIN_NEWTON
	wf.add_vector_form_surf(form_0_surf<double, scalar>, form_0_surf<Ord, Ord>);
#endif
#if defined LIN_DIRICHLET || defined NLN_DIRICHLET
	// preconditioner
	wf.add_matrix_form(precond_0_0<double, scalar>, precond_0_0<Ord, Ord>, HERMES_SYM);
#endif

	// Initialize the FE problem.
	DiscreteProblem fep(&wf, &space);

#if defined LIN_DIRICHLET || defined NLN_DIRICHLET
	// use ML preconditioner to speed-up things
	MlPrecond pc("sa");
	pc.set_param("max levels", 6);
	pc.set_param("increasing or decreasing", "decreasing");
	pc.set_param("aggregation: type", "MIS");
	pc.set_param("coarse: type", "Amesos-KLU");
#endif

	NoxSolver solver(&fep);
#if defined LIN_DIRICHLET || defined NLN_DIRICHLET
//	solver.set_precond(&pc);
#endif

	info("Solving.");
	Solution sln(&mesh);
	if(solver.solve()) Solution::vector_to_solution(solver.get_solution(), &space, &sln);
  else error ("Matrix solver failed.\n");
	

		Solution ex_sln(&mesh);
		ex_sln.set_exact(exact_solution);

		// Calculate exact error.
  info("Calculating exact error.");
  Adapt *adaptivity = new Adapt(&space, HERMES_H1_NORM);
  bool solutions_for_adapt = false;
  double err_exact = adaptivity->calc_err_exact(&sln, &ex_sln, solutions_for_adapt, HERMES_TOTAL_ERROR_ABS);

  if (err_exact > EPS)
		// Calculated solution is not precise enough.
		success_test = 0;

  if (success_test) {
    info("Success!");
    return ERR_SUCCESS;
  }
  else {
    info("Failure!");
    return ERR_FAILURE;
  }
}