Exemple #1
0
double N_from_mu(Minimizer *min, Grid *potential, const Grid &constraint, double mu) {
  Functional f = constrain(constraint, OfEffectivePotential(HS + IdealGas()
                                                            + ChemicalPotential(mu)));
  double Nnow = 0;
  min->minimize(f, potential->description());
  for (int i=0;i<numiters && min->improve_energy(false);i++) {
    Grid density(potential->description(), EffectivePotentialToDensity()(1, potential->description(), *potential));
    Nnow = density.sum()*potential->description().dvolume;
    printf("Nnow is %g vs %g\n", Nnow, N);
    fflush(stdout);
    
    density.epsNativeSlice("papers/contact/figs/box.eps", 
                           Cartesian(0,ymax+2,0), Cartesian(0,0,zmax+2), 
                           Cartesian(0,-ymax/2-1,-zmax/2-1));
    density.epsNativeSlice("papers/contact/figs/box-diagonal.eps", 
                           Cartesian(xmax+2,0,zmax+2),  Cartesian(0,ymax+2,0),
                           Cartesian(-xmax/2-1,-ymax/2-1,-zmax/2-1));
    //sleep(3);
  }
  return Nnow;
}
Exemple #2
0
void run_with_eta(double eta, const char *name, Functional fhs) {
  // Generates a data file for the pair distribution function, for filling fraction eta
  // and distance of first sphere from wall of z0. Data saved in a table such that the
  // columns are x values and rows are z1 values.
  printf("Now starting run_with_eta with eta = %g name = %s\n",
         eta, name);
  Functional f = OfEffectivePotential(fhs + IdealGas());
  double mu = find_chemical_potential(f, 1, eta/(4*M_PI/3));
  f = OfEffectivePotential(fhs + IdealGas()
                           + ChemicalPotential(mu));
  Lattice lat(Cartesian(width,0,0), Cartesian(0,width,0), Cartesian(0,0,width));
  GridDescription gd(lat, dx);
  Grid potential(gd);
  Grid constraint(gd);
  constraint.Set(notinsphere);
  f = constrain(constraint, f);
  potential = (eta*constraint + 1e-4*eta*VectorXd::Ones(gd.NxNyNz))/(4*M_PI/3);
  potential = -potential.cwise().log();

  const double approx_energy = (fhs + IdealGas() + ChemicalPotential(mu))(1, eta/(4*M_PI/3))*uipow(width,3);
  const double precision = fabs(approx_energy*1e-10);
  //printf("Minimizing to %g absolute precision...\n", precision);
  { // Put mimizer in block so as to free it when we finish minimizing to save memory.
    Minimizer min = Precision(precision,
                              PreconditionedConjugateGradient(f, gd, 1,
                                                              &potential,
                                                              QuadraticLineMinimizer));
    for (int i=0;min.improve_energy(true) && i<100;i++) {
      double peak = peak_memory()/1024.0/1024;
      double current = current_memory()/1024.0/1024;
      printf("Peak memory use is %g M (current is %g M)\n", peak, current);
      fflush(stdout);
    }
    took("Doing the minimization");
  }
  Grid density(gd, EffectivePotentialToDensity()(1, gd, potential));
  Grid gsigma(gd, gSigmaA(1.0)(1, gd, density));
  Grid nA(gd, ShellConvolve(2)(1, density)/(4*M_PI*4));
  Grid n3(gd, StepConvolve(1)(1, density));
  Grid nbar_sokolowski(gd, StepConvolve(1.6)(1, density));
  nbar_sokolowski /= (4.0/3.0*M_PI*ipow(1.6, 3));
  // Create the walls directory if it doesn't exist.
  if (mkdir("papers/pair-correlation/figs/walls", 0777) != 0 && errno != EEXIST) {
    // We failed to create the directory, and it doesn't exist.
    printf("Failed to create papers/pair-correlation/figs/walls: %s",
           strerror(errno));
    exit(1); // fail immediately with error code
  }

  // here you choose the values of z0 to use
  // dx is the resolution at which we compute the density.
  char *plotname = new char[4096];
  for (double z0 = 2.1; z0 < 4.5; z0 += 2.1) {
    // For each z0, we now pick one of our methods for computing the
    // pair distribution function:
    for (int version = 0; version < numplots; version++) {
      sprintf(plotname,
              "papers/pair-correlation/figs/triplet%s-%s-%04.2f-%1.2f.dat",
              name, fun[version], eta, z0);
      FILE *out = fopen(plotname,"w");
      FILE *xfile = fopen("papers/pair-correlation/figs/triplet-x.dat","w");
      FILE *zfile = fopen("papers/pair-correlation/figs/triplet-z.dat","w");
      // the +1 for z0 and z1 are to shift the plot over, so that a sphere touching the wall
      // is at z = 0, to match with the monte carlo data
      const Cartesian r0(0,0,z0);
      for (double x = 0; x < 4; x += dx) {
        for (double z1 = -4; z1 <= 9; z1 += dx) {
          const Cartesian r1(x,0,z1);
          double g2 = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
          double n_bulk = (3.0/4.0/M_PI)*eta;
          double g3 = g2*density(r0)*density(r1)/n_bulk/n_bulk;
          fprintf(out, "%g\t", g3);
          fprintf(xfile, "%g\t", x);
          fprintf(zfile, "%g\t", z1);
        }
        fprintf(out, "\n");
        fprintf(xfile, "\n");
        fprintf(zfile, "\n");
      }
      fclose(out);
      fclose(xfile);
      fclose(zfile);
    }
  }
  delete[] plotname;
  took("Dumping the triplet dist plots");
  const double ds = 0.01; // step size to use in path plots, FIXME increase for publication!
  const double delta = .1; //this is the value of radius of the
                           //particle as it moves around the contact
                           //sphere on its path
  char *plotname_path = new char[4096];
  for (int version = 0; version < numplots; version++) {
    sprintf(plotname_path,
            "papers/pair-correlation/figs/triplet%s-path-%s-%04.2f.dat",
            name, fun[version], eta);
    FILE *out_path = fopen(plotname_path, "w");
    if (!out_path) {
      fprintf(stderr, "Unable to create file %s!\n", plotname_path);
      return;
    }

    sprintf(plotname_path,
            "papers/pair-correlation/figs/triplet-back-contact-%s-%04.2f.dat",
            fun[version], eta);
    FILE *out_back = fopen(plotname_path, "w");
    if (!out_back) {
      fprintf(stderr, "Unable to create file %s!\n", plotname_path);
      return;
    }
    fprintf(out_path, "# unused\tg3\tz\tx\n");
    fprintf(out_back, "# unused\tg3\tz\tx\n");

    const Cartesian r0(0,0, 2.0+delta);
    const double max_theta = M_PI*2.0/3;
    for (double z = 7; z >= 2*(2.0 + delta); z-=ds) {
      const Cartesian r1(0,0,z);
      double g2_path = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
      double n_bulk = (3.0/4.0/M_PI)*eta;
      double g3 = g2_path*density(r0)*density(r1)/n_bulk/n_bulk;
      fprintf(out_path,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
    }
    for (double z = -7; z <= -(2.0 + delta); z+=ds) {
      const Cartesian r1(0,0,z);
      double g2_path = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
      double n_bulk = (3.0/4.0/M_PI)*eta;
      double g3 = g2_path*density(r0)*density(r1)/n_bulk/n_bulk;
      fprintf(out_back,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
    }
    const double dtheta = ds/2;
    for (double theta = 0; theta <= max_theta; theta += dtheta){
      const Cartesian r1((2.0+delta)*sin(theta), 0, (2.0+delta)*(1+cos(theta)));
      double g2_path = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
      double n_bulk = (3.0/4.0/M_PI)*eta;
      double g3 = g2_path*density(r0)*density(r1)/n_bulk/n_bulk;
      fprintf(out_path,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
    }
    for (double theta = 0; theta <= max_theta; theta += dtheta){
      const Cartesian r1((2.0+delta)*sin(theta), 0,-(2.0+delta)*cos(theta));
      double g2_path = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
      double n_bulk = (3.0/4.0/M_PI)*eta;
      double g3 = g2_path*density(r0)*density(r1)/n_bulk/n_bulk;
      fprintf(out_back,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
    }
    for (double x = (2.0+delta)*sqrt(3)/2; x<=6; x+=ds){
      const Cartesian r1(x, 0, 1.0+delta/2);
      double g2_path = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
      double n_bulk = (3.0/4.0/M_PI)*eta;
      double g3 = g2_path*density(r0)*density(r1)/n_bulk/n_bulk;
      fprintf(out_path,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
      fprintf(out_back,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
    }
    fclose(out_path);
    fclose(out_back);
  }
  for (int version = 0; version < numplots; version++) {
    sprintf(plotname_path,
            "papers/pair-correlation/figs/triplet-path-inbetween-%s-%04.2f.dat",
            fun[version], eta);
    FILE *out_path = fopen(plotname_path, "w");
    if (!out_path) {
      fprintf(stderr, "Unable to create file %s!\n", plotname_path);
      return;
    }
    sprintf(plotname_path,
            "papers/pair-correlation/figs/triplet-back-inbetween-%s-%04.2f.dat",
            fun[version], eta);
    FILE *out_back = fopen(plotname_path, "w");
    if (!out_back) {
      fprintf(stderr, "Unable to create file %s!\n", plotname_path);
      return;
    }
    fprintf(out_path, "# unused\tg3\tz\tx\n");
    fprintf(out_back, "# unused\tg3\tz\tx\n");

    const Cartesian r0(0,0, 4.0+2*delta);
    const double max_theta = M_PI;
    for (double z = 11; z >= 3*(2.0 + delta); z-=ds) {
      const Cartesian r1(0,0,z);
      double g2_path = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
      double n_bulk = (3.0/4.0/M_PI)*eta;
      double g3 = g2_path*density(r0)*density(r1)/n_bulk/n_bulk;
      fprintf(out_path,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
    }
    for (double z = -10; z <= -(2.0 + delta); z+=ds) {
      const Cartesian r1(0,0,z);
      double g2_path = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
      double n_bulk = (3.0/4.0/M_PI)*eta;
      double g3 = g2_path*density(r0)*density(r1)/n_bulk/n_bulk;
      fprintf(out_back,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
    }
    const double dtheta = ds/2;
    for (double theta = 0; theta <= max_theta; theta += dtheta){
      const Cartesian r1((2.0+delta)*sin(theta), 0, (2.0+delta)*(2+cos(theta)));
      double g2_path = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
      double n_bulk = (3.0/4.0/M_PI)*eta;
      double g3 = g2_path*density(r0)*density(r1)/n_bulk/n_bulk;
      fprintf(out_path,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
    }
    for (double theta = 0; theta <= max_theta; theta += dtheta){
      const Cartesian r1((2.0+delta)*sin(theta), 0, -(2.0+delta)*cos(theta));
      double g2_path = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
      double n_bulk = (3.0/4.0/M_PI)*eta;
      double g3 = g2_path*density(r0)*density(r1)/n_bulk/n_bulk;
      fprintf(out_back,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
    }
    for (double x = 0; x>=-6; x-=ds){
      const Cartesian r1(x, 0, 2.0+delta);
      double g2_path = pairdists[version](gsigma, density, nA, n3, nbar_sokolowski, r0, r1);
      double n_bulk = (3.0/4.0/M_PI)*eta;
      double g3 = g2_path*density(r0)*density(r1)/n_bulk/n_bulk;
      fprintf(out_path,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
      fprintf(out_back,"0\t%g\t%g\t%g\n", g3, r1[2], r1[0]);
    }
    fclose(out_path);
    fclose(out_back);
  }
  delete[] plotname_path;
}
int main(int, char **argv) {
  const double myT = water_prop.kT; // room temperature in Hartree
  const double R = 2.7;

  Functional x(Identity());
  Grid n(gd);
  n = 0.001*VectorXd::Ones(gd.NxNyNz) + 0.001*(-10*r2(gd)).cwise().exp();

  compare_functionals(Sum(), x + kT, myT, n, 2e-13);

  compare_functionals(Quadratic(), sqr(x + kT) - x + 2*kT, myT, n, 2e-12);

  compare_functionals(Sqrt(), sqrt(x), myT, n, 1e-12);

  compare_functionals(SqrtAndMore(), sqrt(x) - x + 2*kT, myT, n, 1e-12);

  compare_functionals(Log(), log(x), myT, n, 3e-14);

  compare_functionals(LogAndSqr(), log(x) + sqr(x), myT, n, 3e-14);

  compare_functionals(LogAndSqrAndInverse(), log(x) + (sqr(x)-Pow(3)) + Functional(1)/x, myT, n, 3e-10);

  compare_functionals(LogOneMinusX(), log(1-x), myT, n, 1e-12);

  compare_functionals(LogOneMinusNbar(R), log(1-StepConvolve(R)), myT, n, 1e-13);

  compare_functionals(SquareXshell(R), sqr(xShellConvolve(R)), myT, n);

  Functional n2 = ShellConvolve(R);
  Functional n3 = StepConvolve(R);
  compare_functionals(n2_and_n3(R), sqr(n2) + sqr(n3), myT, n, 1e-14);

  const double four_pi_r2 = 4*M_PI*R*R;
  Functional one_minus_n3 = 1 - n3;
  Functional phi1 = (-1/four_pi_r2)*n2*log(one_minus_n3);
  compare_functionals(Phi1(R), phi1, myT, n, 1e-13);

  const double four_pi_r = 4*M_PI*R;
  Functional n2x = xShellConvolve(R);
  Functional n2y = yShellConvolve(R);
  Functional n2z = zShellConvolve(R);
  Functional phi2 = (sqr(n2) - sqr(n2x) - sqr(n2y) - sqr(n2z))/(four_pi_r*one_minus_n3);
  compare_functionals(Phi2(R), phi2, myT, n, 1e-14);

  Functional phi3rf = n2*(sqr(n2) - 3*(sqr(n2x) + sqr(n2y) + sqr(n2z)))/(24*M_PI*sqr(one_minus_n3));
  compare_functionals(Phi3rf(R), phi3rf, myT, n, 1e-13);

  compare_functionals(AlmostRF(R), myT*(phi1 + phi2 + phi3rf), myT, n, 2e-14);

  Functional veff = EffectivePotentialToDensity();
  compare_functionals(SquareVeff(R), sqr(veff), myT, Grid(gd, -myT*n.cwise().log()), 1e-12);

  compare_functionals(AlmostRFnokT(R), phi1 + phi2 + phi3rf, myT, n, 3e-14);

  compare_functionals(AlmostRF(R),
                      (myT*phi1).set_name("phi1") + (myT*phi2).set_name("phi2") + (myT*phi3rf).set_name("phi3"),
                      myT, n, 4e-14);

  compare_functionals(Phi1Veff(R), phi1(veff), myT, Grid(gd, -myT*n.cwise().log()), 1e-13);

  compare_functionals(Phi2Veff(R), phi2(veff), myT, Grid(gd, -myT*n.cwise().log()), 1e-14);

  compare_functionals(Phi3rfVeff(R), phi3rf(veff), myT, Grid(gd, -myT*n.cwise().log()), 1e-13);

  compare_functionals(IdealGasFast(), IdealGasOfVeff, myT, Grid(gd, -myT*n.cwise().log()),
                      1e-12);

  double mu = -1;
  compare_functionals(Phi1plus(R, mu),
                      phi1(veff) + IdealGasOfVeff + ChemicalPotential(mu)(veff),
                      myT, Grid(gd, -myT*n.cwise().log()), 1e-12);

  if (errors == 0) printf("\n%s passes!\n", argv[0]);
  else printf("\n%s fails %d tests!\n", argv[0], errors);
  return errors;
}
Exemple #4
0
int main(int, char **) {
    for (double eta = 0.3; eta < 0.35; eta += 0.1) {
        // Generates a data file for the pair distribution function, for filling fraction eta
        // and distance of first sphere from wall of z0. Data saved in a table such that the
        // columns are x values and rows are z1 values.
        printf("Now starting sphere_with_wall with eta = %g\n",eta);
        Lattice lat(Cartesian(width,0,0), Cartesian(0,width,0), Cartesian(0,0,width+2*spacing));
        GridDescription gd(lat, dx); //the resolution here dramatically affects our memory use

        Functional f = OfEffectivePotential(WB + IdealGas());
        double mu = find_chemical_potential(f, 1, eta/(4*M_PI/3));
        f = OfEffectivePotential(WB + IdealGas()
                                 + ChemicalPotential(mu));

        Grid potential(gd);
        Grid constraint(gd);

        constraint.Set(*notinwall_or_sphere);
        constraint.epsNativeSlice("myconstraint.eps",
                                  Cartesian(0, 0, 2*(width+2*spacing)),
                                  Cartesian(2*width, 0, 0),
                                  Cartesian(0, 0, 0));

        f = constrain(constraint, f);

        potential = (eta*constraint + 1e-4*eta*VectorXd::Ones(gd.NxNyNz))/(4*M_PI/3);
        potential = -potential.cwise().log();

        const double approx_energy = (WB + IdealGas() + ChemicalPotential(mu))(1, eta/(4*M_PI/3))*dw*dw*width;
        const double precision = fabs(approx_energy*1e-4);
        //printf("Minimizing to %g absolute precision...\n", precision);
        Minimizer min = Precision(precision,
                                  PreconditionedConjugateGradient(f, gd, 1,
                                          &potential,
                                          QuadraticLineMinimizer));
        {
            double peak = peak_memory()/1024.0/1024;
            double current = current_memory()/1024.0/1024;
            printf("Peak memory use is %g M (current is %g M)\n", peak, current);
            fflush(stdout);
        }

        for (int i=0; min.improve_energy(true) && i<100; i++) {
            double peak = peak_memory()/1024.0/1024;
            double current = current_memory()/1024.0/1024;
            printf("Peak memory use is %g M (current is %g M)\n", peak, current);
            fflush(stdout);
        }
        Grid density(gd, EffectivePotentialToDensity()(1, gd, potential));

        char *plotname = new char[1024];
        sprintf(plotname, "papers/pair-correlation/figs/walls/wallsWB-sphere-dft-%04.2f.dat", eta);
        pair_plot(plotname, density);
        delete[] plotname;

        char *plotname_path = new char[1024];
        sprintf(plotname_path, "papers/pair-correlation/figs/walls/wallsWB-sphere-dft-path-%04.2f.dat", eta);
        path_plot(plotname_path, density, constraint);
        delete[] plotname_path;
        fflush(stdout);
        {
            double peak = peak_memory()/1024.0/1024;
            double current = current_memory()/1024.0/1024;
            printf("Peak memory use is %g M (current is %g M)\n", peak, current);
            fflush(stdout);
        }
        fflush(stdout);
    }
    fflush(stdout);
    // Just create this file so make knows we have run.
    if (!fopen("papers/pair-correlation/figs/walls_sphere.dat", "w")) {
        printf("Error creating walls.dat!\n");
        return 1;
    }
    fflush(stdout);
    return 1;
}
Exemple #5
0
int main(int argc, char *argv[]) {
  if (argc == 5) {
    if (sscanf(argv[1], "%lg", &xmax) != 1) {
      printf("Got bad x argument: %s\n", argv[1]);
      return 1;
    }
    if (sscanf(argv[2], "%lg", &ymax) != 1) {
      printf("Got bad y argument: %s\n", argv[2]);
      return 1;
    }
    if (sscanf(argv[3], "%lg", &zmax) != 1) {
      printf("Got bad z argument: %s\n", argv[3]);
      return 1;
    }
    if (sscanf(argv[4], "%lg", &N) != 1) {
      printf("Got bad N argument: %s\n", argv[4]);
      return 1;
    }
    using_default_box = false;
    printf("Box is %g x %g x %g hard sphere diameters, and it holds %g of them\n", xmax, ymax, zmax, N);
  }

  char *datname = (char *)malloc(1024);
  sprintf(datname, "papers/contact/figs/box-%02.0f,%02.0f,%02.0f-%02.0f-energy.dat", xmax, ymax, zmax, N);
  
  FILE *o = fopen(datname, "w");

  const double myvolume = (xmax+2)*(ymax+2)*(zmax+2);
  const double meandensity = N/myvolume;

  Functional f = OfEffectivePotential(HS + IdealGas());
  double mu = find_chemical_potential(f, 1, meandensity);
  f = OfEffectivePotential(HS + IdealGas()
                           + ChemicalPotential(mu));

  Lattice lat(Cartesian(xmax+3,0,0), Cartesian(0,ymax+3,0), Cartesian(0,0,zmax+3));
  GridDescription gd(lat, 0.05);
    
  Grid potential(gd);
  Grid constraint(gd);
  constraint.Set(notinwall);
  took("Setting the constraint");

  printf("xmax = %g\nymax = %g\nzmax = %g\nmeandensity=%g\n", xmax, ymax, zmax, meandensity);
  f = constrain(constraint, f);
  constraint.epsNativeSlice("papers/contact/figs/box-constraint.eps",
   			      Cartesian(0,ymax+4,0), Cartesian(0,0,zmax+4), 
   			      Cartesian(0,-ymax/2-2,-zmax/2-2));
  printf("Constraint has become a graph!\n");
  
  potential = meandensity*constraint + 1e-4*meandensity*VectorXd::Ones(gd.NxNyNz);
  potential = -potential.cwise().log();
    
  Minimizer min = Precision(1e-6, 
                            PreconditionedConjugateGradient(f, gd, 1, 
                                                            &potential,
                                                            QuadraticLineMinimizer));
    
  double mumax = mu, mumin = mu, dmu = 4.0/N;
  double Nnow = N_from_mu(&min, &potential, constraint, mu);
  const double fraccuracy = 1e-3;
  if (fabs(Nnow/N - 1) > fraccuracy) {
    if (Nnow > N) {
      while (Nnow > N) {
        mumin = mumax;
        mumax += dmu;
        dmu *= 2;
        
        Nnow = N_from_mu(&min, &potential, constraint, mumax);
        // Grid density(gd, EffectivePotentialToDensity()(1, gd, potential));
        // density = EffectivePotentialToDensity()(1, gd, potential);
        // density.epsNativeSlice("papers/contact/figs/box.eps", 
        //                        Cartesian(0,ymax+2,0), Cartesian(0,0,zmax+2), 
        //                        Cartesian(0,-ymax/2-1,-zmax/2-1));
        // density.epsNativeSlice("papers/contact/figs/box-diagonal.eps", 
        //                        Cartesian(xmax+2,0,zmax+2),  Cartesian(0,ymax+2,0),
        //                        Cartesian(-xmax/2-1,-ymax/2-1,-zmax/2-1));
        printf("mumax %g gives N %g\n", mumax, Nnow);
        took("Finding N from mu");
      }
      printf("mu is between %g and %g\n", mumin, mumax);
    } else {
      while (Nnow < N) {
        mumax = mumin;
        if (mumin > dmu) {
          mumin -= dmu;
          dmu *= 2;
        } else if (mumin > 0) {
          mumin = -mumin;
        } else {
          mumin *= 2;
        }
        
        Nnow = N_from_mu(&min, &potential, constraint, mumin);
        // density = EffectivePotentialToDensity()(1, gd, potential);
        // density.epsNativeSlice("papers/contact/figs/box.eps", 
        //                        Cartesian(0,ymax+2,0), Cartesian(0,0,zmax+2), 
        //                        Cartesian(0,-ymax/2-1,-zmax/2-1));
        // density.epsNativeSlice("papers/contact/figs/box-diagonal.eps", 
        //                        Cartesian(xmax+2,0,zmax+2),  Cartesian(0,ymax+2,0),
        //                        Cartesian(-xmax/2-1,-ymax/2-1,-zmax/2-1));
        printf("mumin %g gives N %g\n", mumin, Nnow);
        took("Finding N from mu");
      }
      printf("mu is between %g and %g\n", mumin, mumax);
    }
    
    while (fabs(N/Nnow-1) > fraccuracy) {
      mu = 0.5*(mumin + mumax);
      Nnow = N_from_mu(&min, &potential, constraint, mu);
      // density = EffectivePotentialToDensity()(1, gd, potential);
      // density.epsNativeSlice("papers/contact/figs/box.eps", 
      //                        Cartesian(0,ymax+2,0), Cartesian(0,0,zmax+2), 
      //                        Cartesian(0,-ymax/2-1,-zmax/2-1));
      // density.epsNativeSlice("papers/contact/figs/box-diagonal.eps", 
      //                        Cartesian(xmax+2,0,zmax+2),  Cartesian(0,ymax+2,0),
      //                        Cartesian(-xmax/2-1,-ymax/2-1,-zmax/2-1));
      printf("Nnow is %g vs %g with mu %g\n", Nnow, N, mu);
      took("Finding N from mu");
      if (Nnow > N) {
        mumin = mu;
      } else {
        mumax = mu;
      }
    }
  }
  printf("N final is %g (vs %g) with mu = %g\n", Nnow, N, mu);

  double energy = min.energy();
  printf("Energy is %.15g\n", energy);

  Grid density(gd, EffectivePotentialToDensity()(1, gd, potential));
  double mean_contact_density = ContactDensitySimplest(1.0).integral(1, density)/myvolume;
  
  fprintf(o, "%g\t%g\t%g\t%.15g\t%.15g\n", xmax, ymax, zmax, energy, mean_contact_density);
  
  Grid energy_density(gd, f(1, gd, potential));
  Grid contact_density(gd, ContactDensitySimplest(1.0)(1, gd, density));
  Grid n0(gd, ShellConvolve(1)(1, density));
  Grid wu_contact_density(gd, FuWuContactDensity(1.0)(1, gd, density));
  char *plotname = (char *)malloc(1024);
  sprintf(plotname, "papers/contact/figs/box-100c--%02.0f,%02.0f,%02.0f-%02.0f.dat", xmax, ymax, zmax, N);
  plot_grids_100_center(plotname, density, energy_density, contact_density);
  sprintf(plotname, "papers/contact/figs/box-100s--%02.0f,%02.0f,%02.0f-%02.0f.dat", xmax, ymax, zmax, N);
  plot_grids_100_side(plotname, density, energy_density, contact_density);
  sprintf(plotname, "papers/contact/figs/box-110c--%02.0f,%02.0f,%02.0f-%02.0f.dat", xmax, ymax, zmax, N);
  plot_grids_110(plotname, density, energy_density, contact_density);
  sprintf(plotname, "papers/contact/figs/box-x-%02.0f,%02.0f,%02.0f-%02.0f.dat", xmax, ymax, zmax, N);
  x_plot(plotname, density, energy_density, contact_density, wu_contact_density);
  free(plotname);
  density.epsNativeSlice("papers/contact/figs/box.eps", 
                         Cartesian(0,ymax+2,0), Cartesian(0,0,zmax+2), 
                         Cartesian(0,-ymax/2-1,-zmax/2-1));
  density.epsNativeSlice("papers/contact/figs/box-diagonal.eps", 
                         Cartesian(xmax+2,0,zmax+2),  Cartesian(0,ymax+2,0),
                         Cartesian(-xmax/2-1,-ymax/2-1,-zmax/2-1));
  
  took("Plotting stuff");
  
  fclose(o);
}
Exemple #6
0
int main(int, char **argv) {
  Functional n = EffectivePotentialToDensity();
  double Veff = -hughes_water_prop.kT*log(hughes_water_prop.liquid_density);

  const double nmin = 1e-11, nmax = 0.007;

  {
    double ngas = 2e-5;
    double mu = find_chemical_potential(IdealGasOfVeff(), hughes_water_prop.kT, ngas);
    test_eos("ideal gas", IdealGasOfVeff() + ChemicalPotential(mu)(n), ngas, ngas*hughes_water_prop.kT);
  }

  test_eos("quadratic", 0.5*sqr(n) - n, 1.0, 0.5, 2e-6);
  test_pressure("quadratic(2)", 0.5*sqr(n) - n, 2, 2);
  test_pressure("quadratic(3)", 0.5*sqr(n) - n, 3, 4.5);

  {
    //FILE *o = fopen("ideal-gas.dat", "w");
    //equation_of_state(o, IdealGasOfVeff(), hughes_water_prop.kT, nmin, nmax);
    //fclose(o);
  }

  {
    FILE *o = fopen("dispersion.dat", "w");
    //equation_of_state(o, DispersionSAFT(hughes_water_prop.lengthscale, hughes_water_prop.kT,
    //                                    hughes_water_prop.epsilon_dispersion,
    //                                    hughes_water_prop.lambda_dispersion)(n),
    //                  hughes_water_prop.kT, nmin, nmax);
    fclose(o);
    printf("Got dispersion!\n");

    Functional f = OfEffectivePotential(SaftFluid2(hughes_water_prop.lengthscale,
                                                  hughes_water_prop.epsilonAB, hughes_water_prop.kappaAB,
                                                  hughes_water_prop.epsilon_dispersion,
                                                  hughes_water_prop.lambda_dispersion,
                                                  hughes_water_prop.length_scaling, 0));


    const double n_1atm = pressure_to_density(f, hughes_water_prop.kT, atmospheric_pressure,
					      0.001, 0.01);
    printf("density at 1 atmosphere is %g\n", n_1atm);
    printf("error in density at 1 atmosphere is %g\n", n_1atm/hughes_water_prop.liquid_density - 1);
    if (fabs(n_1atm/hughes_water_prop.liquid_density - 1) > 0.01) {
      printf("FAIL! error in water density is too big! %g\n",
             n_1atm/hughes_water_prop.liquid_density - 1);
      retval++;
    }

    test_pressure("saft at 1 atm", f, n_1atm, atmospheric_pressure);

    {
      printf("working onfoo\n");
      double nv = coexisting_vapor_density(f, hughes_water_prop.kT, hughes_water_prop.liquid_density);
      printf("predicted vapor density: %g\n", nv);
      printf("actual vapor density:    %g\n", hughes_water_prop.vapor_density);
    }

    if (0) {
      o = fopen("saft-fluid.dat", "w");
      double mu = f.derive(hughes_water_prop.kT, Veff)*hughes_water_prop.kT/hughes_water_prop.liquid_density; // convert from derivative w.r.t. V
      equation_of_state(o, f + ChemicalPotential(mu)(n), hughes_water_prop.kT, nmin, nmax);
      fclose(o);
    }

    {
      double nl, nv, mu;
      saturated_liquid_vapor(f, hughes_water_prop.kT, 1e-14, 0.0017, 0.0055, &nl, &nv, &mu, 1e-5);
      printf("saturated water density is %g\n", nl);
      printf("1 atm water density ? is %g\n", hughes_water_prop.liquid_density);
      if (fabs(nl/hughes_water_prop.liquid_density - 1) > 0.1) {
        printf("FAIL: error in saturated water density is too big! %g\n",
               nl/hughes_water_prop.liquid_density - 1);
        retval++;
      }

      printf("predicted saturated vapor density: %g\n", nv);
      printf("actual vapor density:    %g\n", hughes_water_prop.vapor_density);
      //double mu = f.derive(-hughes_water_prop.kT*log(nl))*hughes_water_prop.kT/nl; // convert from derivative w.r.t. V
      //o = fopen("saft-fluid-saturated.dat", "w");
      //equation_of_state(o, f + ChemicalPotential(mu)(n), hughes_water_prop.kT, nmin, 1.1*nl);
      //fclose(o);

      double pv = pressure(f, hughes_water_prop.kT, nv);
      printf("vapor pressure is %g\n", pv);
      if (fabs(pv/hughes_water_prop.kT/nv - 1) > 1e-3) {
        printf("FAIL: error in vapor pressure, steam isn't ideal gas? %g\n",
               pv/hughes_water_prop.kT/nv - 1);
        retval++;
      }
    }

    {
      o = fopen("room-temperature.dat", "w");
      Functional f = OfEffectivePotential(SaftFluid2(hughes_water_prop.lengthscale,
                                                        hughes_water_prop.epsilonAB, hughes_water_prop.kappaAB,
                                                        hughes_water_prop.epsilon_dispersion,
                                                        hughes_water_prop.lambda_dispersion,
                                                        hughes_water_prop.length_scaling, 0));
      double mufoo = find_chemical_potential(f, hughes_water_prop.kT,
                                             hughes_water_prop.liquid_density);
      f = OfEffectivePotential(SaftFluid2(hughes_water_prop.lengthscale,
                                             hughes_water_prop.epsilonAB, hughes_water_prop.kappaAB,
                                             hughes_water_prop.epsilon_dispersion,
                                             hughes_water_prop.lambda_dispersion,
                                             hughes_water_prop.length_scaling, mufoo));
      double nl, nv, mu;
      saturated_liquid_vapor(f, hughes_water_prop.kT, 1e-14, 0.0017, 0.0055, &nl, &nv, &mu, 1e-5);
      for (double dens=0.1*nv; dens<=1.2*nl; dens *= 1.01) {
        double V = -hughes_water_prop.kT*log(dens);
        double Vl = -hughes_water_prop.kT*log(nl);
        fprintf(o, "%g\t%g\t%g\n",
                dens, f(hughes_water_prop.kT, V), f(hughes_water_prop.kT, Vl) - (dens-nl)*mu);
      }
      fclose(o);
      printf("Finished plotting room-temperature.dat...\n");
    }
  }

  {
    FILE *o = fopen("hard-sphere-fluid.dat", "w");
    Functional f = HardSpheresWBnotensor(hughes_water_prop.lengthscale)(n) + IdealGasOfVeff();
    double mu = f.derive(hughes_water_prop.kT, Veff)*hughes_water_prop.kT/hughes_water_prop.liquid_density; // convert from derivative w.r.t. V
    equation_of_state(o, f + ChemicalPotential(mu)(n), hughes_water_prop.kT, nmin, nmax);
    fclose(o);
  }

  if (retval == 0) {
    printf("\n%s passes!\n", argv[0]);
  } else {
    printf("\n%s fails %d tests!\n", argv[0], retval);
    return retval;
  }
}
Exemple #7
0
int main(int, char **argv) {
  {
    // Here I set this test to continue running on its current cpu.
    // This is a slightly hokey trick to try to avoid any timings
    // variation due to NUMA and the process bouncing from one CPU to
    // another.  Ideally we'd figure out a better way to decide on
    // which CPU to use for real jobs.
    cpu_set_t cpus;
    CPU_ZERO(&cpus);
    CPU_SET(sched_getcpu(), &cpus);
    int err = sched_setaffinity(0, sizeof(cpu_set_t), &cpus);
    if (err != 0) {
      printf("Error from sched_setaffinity: %d\n", err);
    }
  }
  // Let's figure out which machine we're running on (since we only
  // want to test CPU time if we have timings for this particular
  // machine).
  gethostname(hn, 80);

  const double kT = hughes_water_prop.kT; // room temperature in Hartree
  const double eta_one = 3.0/(4*M_PI*R*R*R);
  const double nliquid = 0.324*eta_one;
  Functional n = EffectivePotentialToDensity();
  const double mu = find_chemical_potential(HardSpheres(R)(n) + IdealGasOfVeff(), kT, nliquid);

  // Here we set up the lattice.
  const double rmax = rcav*2;
  Lattice lat(Cartesian(0,rmax,rmax), Cartesian(rmax,0,rmax), Cartesian(rmax,rmax,0));
  //Lattice lat(Cartesian(1.4*rmax,0,0), Cartesian(0,1.4*rmax,0), Cartesian(0,0,1.4*rmax));
  GridDescription gd(lat, 0.2);

  last_time = get_time();
  Grid external_potential(gd);
  // Do some pointless stuff so we can get some sort of gauge as to
  // how fast this CPU is, for comparison with other tests.
  for (int i=0; i<10; i++) {
    // Do this more times, to get a more consistent result...
    external_potential = external_potential.Ones(gd.NxNyNz);
    external_potential = external_potential.cwise().exp();
    external_potential = 13*external_potential + 3*external_potential.cwise().square();
    external_potential.fft(); // compute and toss the fft...
  }
  // And now let's set the external_potential up as we'd like it.
  external_potential.Set(incavity);
  external_potential *= 1e9;
  check_peak("Setting", "external potential", NULL, 7, 8);

  Grid constraint(gd);
  constraint.Set(notincavity);
  //Functional f1 = f0 + ExternalPotential(external_potential);
  Functional ff = constrain(constraint, IdealGasOfVeff() + (HardSpheres(R) + ChemicalPotential(mu))(n));
  
  Grid potential(gd, external_potential + 0.005*VectorXd::Ones(gd.NxNyNz));

  double eps = hughes_water_prop.epsilonAB;
  double kappa = hughes_water_prop.kappaAB;

  ff = OfEffectivePotential(SaftFluid2(R, eps, kappa, hughes_water_prop.epsilon_dispersion,
                                       hughes_water_prop.lambda_dispersion, hughes_water_prop.length_scaling, mu));
  check_a_functional("SaftFluid2", ff, potential);

  //ff = OfEffectivePotential(SaftFluid(R, eps, kappa, hughes_water_prop.epsilon_dispersion,
  //                                    hughes_water_prop.lambda_dispersion, hughes_water_prop.length_scaling, mu));
  //check_a_functional("SaftFluid", ff, potential);

  //ff = Association2(R, eps, kappa, hughes_water_prop.epsilon_dispersion,
  //                  hughes_water_prop.lambda_dispersion, hughes_water_prop.length_scaling);
  //check_a_functional("Association2", ff, potential);

  //ff = Association(R, eps, kappa, hughes_water_prop.epsilon_dispersion,
  //                 hughes_water_prop.lambda_dispersion, hughes_water_prop.length_scaling);
  //check_a_functional("Association", ff, potential);

  //ff = Dispersion2(R, hughes_water_prop.epsilon_dispersion,
  //                 hughes_water_prop.lambda_dispersion, hughes_water_prop.length_scaling);
  //check_a_functional("Dispersion2", ff, potential);

  //ff = Dispersion(R, hughes_water_prop.epsilon_dispersion,
  //                hughes_water_prop.lambda_dispersion, hughes_water_prop.length_scaling);
  //check_a_functional("Dispersion", ff, potential);

  ff = constrain(constraint, (HardSpheresWBnotensor(R) + ChemicalPotential(mu))(n) + IdealGasOfVeff());
  check_a_functional("HardSpheresWBnotensor", ff, potential);

  //ff = constrain(constraint, (HardSpheresNoTensor(R) + ChemicalPotential(mu))(n) + IdealGasOfVeff());
  //check_a_functional("HardSphereNoTensor", ff, potential);

  ff = constrain(constraint, (HardSpheresNoTensor2(R) + ChemicalPotential(mu))(n) + IdealGasOfVeff());
  check_a_functional("HardSpheresNoTensor2", ff, potential);

  if (numoops == 0) {
    printf("\n%s has no oopses!\n", argv[0]);
  } else {
    printf("\n%s sort of fails %d tests!\n", argv[0], numoops);
  }
  if (retval == 0) {
    printf("\n%s passes!\n", argv[0]);
  } else {
    printf("\n%s fails %d tests!\n", argv[0], retval);
    return retval;
  }
}