void setup_esp_cost_cube(UniformGrid* ugrid, double* vref, double* weights, double* centers, double* A, double* B, double* C, long ncenter, double rcut, double alpha, double gcut) { Cell* cell = ugrid->get_cell(); Cell* grid_cell = ugrid->get_grid_cell(); double gvol = grid_cell->get_volume(); bool is3d = (cell->get_nvec() == 3); long neq = ncenter + is3d; double* work = new double[neq]; double grid_cart[3]; Cube3Iterator c3i = Cube3Iterator(NULL, ugrid->shape); long i[3]; long npoint = c3i.get_npoint(); for (long ipoint=0; ipoint<npoint; ipoint++) { c3i.set_point(ipoint, i); grid_cart[0] = 0; grid_cart[1] = 0; grid_cart[2] = 0; ugrid->delta_grid_point(grid_cart, i); if (*weights > 0) { double sqrtw = sqrt((*weights)*gvol); // Do some electrostatics for (long icenter=0; icenter<ncenter; icenter++) { double delta[3]; delta[0] = centers[3*icenter] - grid_cart[0]; delta[1] = centers[3*icenter+1] - grid_cart[1]; delta[2] = centers[3*icenter+2] - grid_cart[2]; work[icenter] = sqrtw*pair_electrostatics(delta, cell, rcut, alpha, gcut); } if (is3d) work[ncenter] = sqrtw; // Add to the quadratic cost function double vrefw = (*vref)*sqrtw; for (long ic0=0; ic0<neq; ic0++) { for (long ic1=0; ic1<neq; ic1++) { A[ic0+neq*ic1] += work[ic0]*work[ic1]; } B[ic0] += vrefw*work[ic0]; } *C += vrefw*vrefw; } // move on vref++; weights++; } delete[] work; delete cell; delete grid_cell; }
void dot_multi_moments_cube(long nvector, double** data, UniformGrid* ugrid, double* center, long lmax, long mtype, double* output, long nmoment) { Cell* cell = ugrid->get_cell(); long nvec = cell->get_nvec(); delete cell; if (nvec != 0) { throw std::domain_error("dot_multi_moments_cube only works for non-periodic grids."); } if (lmax<0) { throw std::domain_error("lmax can not be negative."); } if ((mtype < 1) || (mtype > 4)) { throw std::domain_error("mtype should be 1, 2, 3 or 4."); } // reset the output to zero Cube3Iterator c3i = Cube3Iterator(NULL, ugrid->shape); for (long ipoint=c3i.get_npoint()-1; ipoint >= 0; ipoint--) { // do the usual product of integranda double term = data_product(ipoint, nvector, data); output[0] += term; if (lmax > 0) { // construct relative vector long j[3]; c3i.set_point(ipoint, j); double delta[3]; delta[0] = center[0]; delta[1] = center[1]; delta[2] = center[2]; ugrid->delta_grid_point(delta, j); // evaluate polynomials in work array double work[nmoment-1]; fill_polynomials_wrapper(work, delta, lmax, mtype); // add product of polynomial and integrand to output for (long imoment=1; imoment < nmoment; imoment++) { output[imoment] += term*work[imoment-1]; } } } }
void compute_esp_cube(UniformGrid* ugrid, double* esp, double* centers, double* charges, long ncenter, double rcut, double alpha, double gcut) { double grid_cart[3]; Cube3Iterator c3i = Cube3Iterator(NULL, ugrid->shape); long i[3]; long npoint = c3i.get_npoint(); Cell* cell = ugrid->get_cell(); for (long ipoint=0; ipoint<npoint; ipoint++) { // Compute the position of the grid point c3i.set_point(ipoint, i); grid_cart[0] = 0; grid_cart[1] = 0; grid_cart[2] = 0; ugrid->delta_grid_point(grid_cart, i); // Do some ewald stuff double tmp = 0; for (long icenter=0; icenter<ncenter; icenter++) { double delta[3]; delta[0] = centers[3*icenter] - grid_cart[0]; delta[1] = centers[3*icenter+1] - grid_cart[1]; delta[2] = centers[3*icenter+2] - grid_cart[2]; tmp += charges[icenter]*pair_electrostatics(delta, cell, rcut, alpha, gcut); } (*esp) = tmp; // move on esp++; } delete cell; }