Exemplo n.º 1
0
int matrix3x3_inverse(const matrix3x3* matrix, matrix3x3* result){
	double det = matrix3x3_determinant(matrix);
	if (det==0) return -1;

	double invdet=1/det;

	matrix3x3 matrix_t;

	if (matrix==result){
		matrix3x3_copy(matrix, &matrix_t);
		matrix=&matrix_t;
	}

	result->m[0][0] = (matrix->m[1][1] * matrix->m[2][2] - matrix->m[2][1] * matrix->m[1][2]) * invdet;
	result->m[0][1] = -(matrix->m[0][1] * matrix->m[2][2] - matrix->m[2][1] * matrix->m[0][2]) * invdet;
	result->m[0][2] = (matrix->m[0][1] * matrix->m[1][2] - matrix->m[1][1] * matrix->m[0][2]) * invdet;

	result->m[1][0] = -(matrix->m[1][0] * matrix->m[2][2] - matrix->m[2][0] * matrix->m[1][2]) * invdet;
	result->m[1][1] = (matrix->m[0][0] * matrix->m[2][2] - matrix->m[2][0] * matrix->m[0][2]) * invdet;
	result->m[1][2] = -(matrix->m[0][0] * matrix->m[1][2] - matrix->m[1][0] * matrix->m[0][2]) * invdet;

	result->m[2][0] = (matrix->m[1][0] * matrix->m[2][1] - matrix->m[2][0] * matrix->m[1][1]) * invdet;
	result->m[2][1] = -(matrix->m[0][0] * matrix->m[2][1] - matrix->m[2][0] * matrix->m[0][1]) * invdet;
	result->m[2][2] = (matrix->m[0][0] * matrix->m[1][1] - matrix->m[1][0] * matrix->m[0][1]) * invdet;

	return 0;
}
Exemplo n.º 2
0
/* Initialize the dielectric function of the global mdata structure,
   along with other geometry data.  Should be called from init-params,
   or in general when global input vars have been loaded and mdata
   allocated. */
void init_epsilon(void)
{
     int i;
     int tree_depth, tree_nobjects;
     number no_size; 

     no_size = 2.0 / ctl_get_number("infinity");

     mpi_one_printf("Mesh size is %d.\n", mesh_size);

     no_size_x = geometry_lattice.size.x <= no_size;
     no_size_y = geometry_lattice.size.y <= no_size || dimensions < 2;
     no_size_z = geometry_lattice.size.z <= no_size || dimensions < 3;

     Rm.c0 = vector3_scale(no_size_x ? 1 : geometry_lattice.size.x, 
			   geometry_lattice.basis.c0);
     Rm.c1 = vector3_scale(no_size_y ? 1 : geometry_lattice.size.y, 
			   geometry_lattice.basis.c1);
     Rm.c2 = vector3_scale(no_size_z ? 1 : geometry_lattice.size.z, 
			   geometry_lattice.basis.c2);
     mpi_one_printf("Lattice vectors:\n");
     mpi_one_printf("     (%g, %g, %g)\n", Rm.c0.x, Rm.c0.y, Rm.c0.z);  
     mpi_one_printf("     (%g, %g, %g)\n", Rm.c1.x, Rm.c1.y, Rm.c1.z);
     mpi_one_printf("     (%g, %g, %g)\n", Rm.c2.x, Rm.c2.y, Rm.c2.z);
     Vol = fabs(matrix3x3_determinant(Rm));
     mpi_one_printf("Cell volume = %g\n", Vol);
  
     Gm = matrix3x3_inverse(matrix3x3_transpose(Rm));
     mpi_one_printf("Reciprocal lattice vectors (/ 2 pi):\n");
     mpi_one_printf("     (%g, %g, %g)\n", Gm.c0.x, Gm.c0.y, Gm.c0.z);  
     mpi_one_printf("     (%g, %g, %g)\n", Gm.c1.x, Gm.c1.y, Gm.c1.z);
     mpi_one_printf("     (%g, %g, %g)\n", Gm.c2.x, Gm.c2.y, Gm.c2.z);
     
     if (eigensolver_nwork > MAX_NWORK) {
	  mpi_one_printf("(Reducing nwork = %d to maximum: %d.)\n",
		 eigensolver_nwork, MAX_NWORK);
	  eigensolver_nwork = MAX_NWORK;
     }

     matrix3x3_to_arr(R, Rm);
     matrix3x3_to_arr(G, Gm);

     /* we must do this to correct for a non-orthogonal lattice basis: */
     geom_fix_objects();

     mpi_one_printf("Geometric objects:\n");
     if (mpi_is_master())
	  for (i = 0; i < geometry.num_items; ++i) {
	       display_geometric_object_info(5, geometry.items[i]);
	       
	       if (geometry.items[i].material.which_subclass == MEDIUM)
		    printf("%*sepsilon = %g, mu = %g\n",
			   5 + 5, "",
			   geometry.items[i].material.
			   subclass.medium_data->epsilon,
			   geometry.items[i].material.
			   subclass.medium_data->mu);
	  }

     destroy_geom_box_tree(geometry_tree);  /* destroy any tree from
					       previous runs */
     {
	  geom_box b0;
	  b0.low = vector3_plus(geometry_center,
				vector3_scale(-0.5, geometry_lattice.size));
	  b0.high = vector3_plus(geometry_center,
				 vector3_scale(0.5, geometry_lattice.size));
	  /* pad tree boundaries to allow for sub-pixel averaging */
	  b0.low.x -= geometry_lattice.size.x / mdata->nx;
	  b0.low.y -= geometry_lattice.size.y / mdata->ny;
	  b0.low.z -= geometry_lattice.size.z / mdata->nz;
	  b0.high.x += geometry_lattice.size.x / mdata->nx;
	  b0.high.y += geometry_lattice.size.y / mdata->ny;
	  b0.high.z += geometry_lattice.size.z / mdata->nz;
	  geometry_tree = create_geom_box_tree0(geometry, b0);
     }
     if (verbose && mpi_is_master()) {
	  printf("Geometry object bounding box tree:\n");
	  display_geom_box_tree(5, geometry_tree);
     }
     geom_box_tree_stats(geometry_tree, &tree_depth, &tree_nobjects);
     mpi_one_printf("Geometric object tree has depth %d and %d object nodes"
	    " (vs. %d actual objects)\n",
	    tree_depth, tree_nobjects, geometry.num_items);

     reset_epsilon();
}