def test(self): system = self.es pi = math.pi box_x = 6 box_y = 6 width = 50 padding = 6 box_z = width + 2 * padding # Set the electrokinetic parameters agrid = 1.0 dt = 1.0 / 7. force = 0.13 sigma = -0.05 viscosity_kinematic = 2.3 friction = 4.3 temperature = 2.9 bjerrum_length = 0.47 temperature_LB = agrid * agrid / (3.0 * dt * dt) kB_LB = 1.0 cs_squared = (1.0 / 3.0) * (agrid * agrid / (dt * dt)) system.box_l = [box_x, box_y, box_z] # Set the simulation parameters system.time_step = dt system.cell_system.skin = 0.1 system.thermostat.turn_off() integration_length = 10000 # Output density, velocity, and pressure tensor profiles output_profiles = 1 # Set up the charged and neutral species density_water = 26.15 density_counterions = -2.0 * float(sigma) / float(width) valency = 1.0 # Set up the (LB) electrokinetics fluid ek = electrokinetics.Electrokinetics(agrid=agrid, lb_density=density_water, viscosity=viscosity_kinematic, friction=friction, T=temperature, prefactor=bjerrum_length * temperature, stencil="nonlinear") counterions = electrokinetics.Species(density=density_counterions, D=0.3, valency=valency, ext_force=[force, 0, 0]) ek.add_species(counterions) # Set up the walls confining the fluid and carrying charge ek_wall1 = electrokinetics.EKBoundary( charge_density=sigma / (agrid * padding), shape=shapes.Wall(normal=[0, 0, 1], dist=padding)) system.ekboundaries.add(ek_wall1) ek_wall2 = electrokinetics.EKBoundary( charge_density=sigma / (agrid * padding), shape=shapes.Wall(normal=[0, 0, -1], dist=-(padding + width))) system.ekboundaries.add(ek_wall2) system.actors.add(ek) # Integrate the system system.integrator.run(integration_length) # compare the various quantities to the analytic results total_velocity_difference = 0.0 total_density_difference = 0.0 total_pressure_difference_xx = 0.0 total_pressure_difference_yy = 0.0 total_pressure_difference_zz = 0.0 total_pressure_difference_xy = 0.0 total_pressure_difference_yz = 0.0 total_pressure_difference_xz = 0.0 # initial parameters for bisection scheme size = pi / (2.0 * width) pnt0 = 0.0 pntm = pnt0 + size pnt1 = pnt0 + 1.9 * size # the bisection scheme tol = 1.0e-08 while (size > tol): val0 = solve(pnt0, width, bjerrum_length, sigma, valency) val1 = solve(pnt1, width, bjerrum_length, sigma, valency) valm = solve(pntm, width, bjerrum_length, sigma, valency) if (val0 < 0.0 and val1 > 0.0): if (valm < 0.0): pnt0 = pntm size = size / 2.0 pntm = pnt0 + size else: pnt1 = pntm size = size / 2.0 pntm = pnt1 - size elif (val0 > 0.0 and val1 < 0.0): if (valm < 0.0): pnt1 = pntm size = size / 2.0 pntm = pnt1 - size else: pnt0 = pntm size = size / 2.0 pntm = pnt0 + size else: sys.exit( "Bisection method fails:\nTuning of domain boundaries may be required." ) # obtain the desired xi value xi = pntm if (output_profiles): fp = open("ek_eof_profile.dat", "w") for i in range(int(box_z / agrid)): if (i * agrid >= padding and i * agrid < box_z - padding): xvalue = i * agrid - padding position = i * agrid - padding - width / 2.0 + agrid / 2.0 # density measured_density = counterions[int(box_x / (2 * agrid)), int(box_y / (2 * agrid)), i].density calculated_density = density(position, xi, bjerrum_length) density_difference = abs(measured_density - calculated_density) total_density_difference = total_density_difference + density_difference # velocity measured_velocity = ek[int(box_x / (2 * agrid)), int(box_y / (2 * agrid)), i].velocity[0] calculated_velocity = velocity(position, xi, width, bjerrum_length, force, viscosity_kinematic, density_water) velocity_difference = abs(measured_velocity - calculated_velocity) total_velocity_difference = total_velocity_difference + velocity_difference # diagonal pressure tensor measured_pressure_xx = ek[int(box_x / (2 * agrid)), int(box_y / (2 * agrid)), i].pressure[(0, 0)] calculated_pressure_xx = hydrostatic_pressure_non_lin( ek, position, xi, bjerrum_length, (0, 0), box_x, box_y, box_z, agrid, temperature) measured_pressure_yy = ek[int(box_x / (2 * agrid)), int(box_y / (2 * agrid)), i].pressure[(1, 1)] calculated_pressure_yy = hydrostatic_pressure_non_lin( ek, position, xi, bjerrum_length, (1, 1), box_x, box_y, box_z, agrid, temperature) measured_pressure_zz = ek[int(box_x / (2 * agrid)), int(box_y / (2 * agrid)), i].pressure[(2, 2)] calculated_pressure_zz = hydrostatic_pressure_non_lin( ek, position, xi, bjerrum_length, (2, 2), box_x, box_y, box_z, agrid, temperature) pressure_difference_xx = abs(measured_pressure_xx - calculated_pressure_xx) pressure_difference_yy = abs(measured_pressure_yy - calculated_pressure_yy) pressure_difference_zz = abs(measured_pressure_zz - calculated_pressure_zz) total_pressure_difference_xx = total_pressure_difference_xx + pressure_difference_xx total_pressure_difference_yy = total_pressure_difference_yy + pressure_difference_yy total_pressure_difference_zz = total_pressure_difference_zz + pressure_difference_zz # xy component pressure tensor measured_pressure_xy = ek[int(box_x / (2 * agrid)), int(box_y / (2 * agrid)), i].pressure[(0, 1)] calculated_pressure_xy = 0.0 pressure_difference_xy = abs(measured_pressure_xy - calculated_pressure_xy) total_pressure_difference_xy = total_pressure_difference_xy + pressure_difference_xy # yz component pressure tensor measured_pressure_yz = ek[int(box_x / (2 * agrid)), int(box_y / (2 * agrid)), i].pressure[(1, 2)] calculated_pressure_yz = 0.0 pressure_difference_yz = abs(measured_pressure_yz - calculated_pressure_yz) total_pressure_difference_yz = total_pressure_difference_yz + pressure_difference_yz # xz component pressure tensor measured_pressure_xz = ek[int(box_x / (2 * agrid)), int(box_y / (2 * agrid)), i].pressure[(0, 2)] calculated_pressure_xz = pressure_tensor_offdiagonal( position, xi, bjerrum_length, force) pressure_difference_xz = abs(measured_pressure_xz - calculated_pressure_xz) total_pressure_difference_xz = total_pressure_difference_xz + pressure_difference_xz if (output_profiles): fp.write( "{} {} {} {} {} {} {} {} {} {} {} {} {} {} {} {} {}\n". format(position, measured_density, calculated_density, measured_velocity, calculated_velocity, measured_pressure_xy, calculated_pressure_xy, measured_pressure_yz, calculated_pressure_yz, measured_pressure_xz, calculated_pressure_xz, measured_pressure_xx, calculated_pressure_xx, measured_pressure_yy, calculated_pressure_yy, measured_pressure_zz, calculated_pressure_zz)) if (output_profiles): fp.close total_density_difference = agrid * total_density_difference / width total_velocity_difference = agrid * total_velocity_difference / width total_pressure_difference_xx = agrid * total_pressure_difference_xx / width total_pressure_difference_yy = agrid * total_pressure_difference_yy / width total_pressure_difference_zz = agrid * total_pressure_difference_zz / width total_pressure_difference_xy = agrid * total_pressure_difference_xy / width total_pressure_difference_yz = agrid * total_pressure_difference_yz / width total_pressure_difference_xz = agrid * total_pressure_difference_xz / width print("Density deviation: {}".format(total_density_difference)) print("Velocity deviation: {}".format(total_velocity_difference)) print("Pressure deviation xx component: {}".format( total_pressure_difference_xx)) print("Pressure deviation yy component: {}".format( total_pressure_difference_yy)) print("Pressure deviation zz component: {}".format( total_pressure_difference_zz)) print("Pressure deviation xy component: {}".format( total_pressure_difference_xy)) print("Pressure deviation yz component: {}".format( total_pressure_difference_yz)) print("Pressure deviation xz component: {}".format( total_pressure_difference_xz)) self.assertLess(total_density_difference, 8.0e-06, "Density accuracy not achieved") self.assertLess(total_velocity_difference, 3.0e-06, "Velocity accuracy not achieved") self.assertLess(total_pressure_difference_xx, 6.0e-05, "Pressure accuracy xx component not achieved") self.assertLess(total_pressure_difference_yy, 8.0e-05, "Pressure accuracy yy component not achieved") self.assertLess(total_pressure_difference_zz, 8.0e-05, "Pressure accuracy zz component not achieved") self.assertLess(total_pressure_difference_xy, 1.0e-10, "Pressure accuracy xy component not achieved") self.assertLess(total_pressure_difference_yz, 1.0e-10, "Pressure accuracy yz component not achieved") self.assertLess(total_pressure_difference_xz, 2.0e-05, "Pressure accuracy xz component not achieved")
system = System(box_l=[10, 10, 10]) system.set_random_state_PRNG() #system.seed = system.cell_system.get_state()['n_nodes'] * [1234] system.cell_system.skin = 0.4 system.time_step = 0.1 ek = electrokinetics.Electrokinetics(lb_density=1, friction=1, agrid=1, viscosity=1, T=1, prefactor=1) pos = electrokinetics.Species(density=0.05, D=0.1, valency=1, ext_force_density=[0, 0, 1.]) neg = electrokinetics.Species(density=0.05, D=0.1, valency=-1, ext_force_density=[0, 0, -1.]) ek.add_species(pos) ek.add_species(neg) system.actors.add(ek) print(ek.get_params()) print(pos.get_params()) print(neg.get_params()) print(pos[5, 5, 5].density) ek_wall_left = electrokinetics.EKBoundary(shape=shapes.Wall(dist=1,
def test(self): system = self.es # Set parameters box_x = 16 box_y = 16 box_z = 16 time_step = 0.001 rho0 = 27.0 diff = 1.0 agrid = 1.0 system.box_l = box_l = [box_x, box_y, box_z] system.time_step = time_step system.cell_system.skin = 0.2 system.thermostat.turn_off() # Setup the Fluid ek = electrokinetics.Electrokinetics(agrid=agrid, lb_density=1.0, viscosity=1.0, friction=0.0, T=1.0, prefactor=1.0, stencil='linkcentered', advection=False, fluctuations=True, fluctuation_amplitude=1.0) species = electrokinetics.Species(density=rho0, D=diff, valency=0.0) ek.add_species(species) system.actors.add(ek) # Warm - Up system.integrator.run(1000) # Set integration and binning parameters n_min = 10.0 n_max = 44.0 bin_size = 0.25 bins = np.zeros(int((n_max - n_min) / bin_size)) x_range = np.linspace(n_min, n_max, int((n_max - n_min) / bin_size)) sample_steps = 100 integration_steps = 200 count = 0 # Integrate for t in range(sample_steps): system.integrator.run(integration_steps) for i in range(box_x): for j in range(box_y): for k in range(box_z): dens = species[i, j, k].density if dens < n_max and dens > n_min: x = int((dens - n_min) / bin_size) bins[x] += 1 count += 1 bins = bins / count / bin_size # Analysis p = [] for i in x_range: p.append(1.0 / (math.sqrt(2.0 * math.pi * i)) * math.pow(rho0 / i, i) * math.exp(i - rho0)) max_diff = 0.0 for i in range(len(x_range)): max_diff = max(math.fabs(p[i] - bins[i]), max_diff) self.assertLess(max_diff, 5.0e-03, "Density distribution accuracy not achieved, allowed " "deviation: 5.0e-03, measured: {}".format(max_diff))
integration_length = 2000 # Set up the (LB) electrokinetics fluid viscosity_kinematic = viscosity_dynamic / density_water ek = electrokinetics.Electrokinetics(agrid=agrid, lb_density=density_water, viscosity=viscosity_kinematic, friction=1.0, T=kT, prefactor=bjerrum_length) # Set up the charged and neutral species density_counterions = -2.0 * sigma / width counterions = electrokinetics.Species( density=density_counterions, D=D, valency=valency, ext_force_density=[ext_force_density, 0, 0]) ek.add_species(counterions) # Set up the walls confining the fluid ek_wall_left = espressomd.ekboundaries.EKBoundary(charge_density=sigma / agrid, shape=shapes.Wall( normal=[0, 0, 1], dist=padding)) ek_wall_right = espressomd.ekboundaries.EKBoundary( charge_density=sigma / agrid, shape=shapes.Wall(normal=[0, 0, -1], dist=-(padding + width))) system.ekboundaries.add(ek_wall_left)
def test(self): system = self.es # Set parameters box_x = 20 box_y = 20 box_z = 20 system.box_l = box_l = [box_x, box_y, box_z] system.cell_system.skin = 0.2 system.time_step = 0.1 system.periodicity = [1, 1, 1] coulomb_accuracy = 1.0e-4 bjerrum_length = 2.13569 agrid = 0.5 system.thermostat.turn_off() # Setup the Fluid ek = electrokinetics.Electrokinetics(agrid=agrid, lb_density=1.0, viscosity=1.0, friction=1.0, T=1.0, prefactor=bjerrum_length, stencil="linkcentered", advection=False, es_coupling=True) positive_ions = electrokinetics.Species(density=0.0, D=0.0, valency=1.0) negative_ions = electrokinetics.Species(density=0.0, D=0.0, valency=-1.0) ek.add_species(positive_ions) ek.add_species(negative_ions) system.actors.add(ek) ################################################################## # X # Setup EK species for i in range(int(box_y / agrid)): for j in range(int(box_z / agrid)): positive_ions[10, i, j].density = 1.0 / agrid negative_ions[30, i, j].density = 1.0 / agrid # Setup MD particle and integrate system.part.add(id=0, pos=[0, 0, 0], q=-1.0, type=0) force_difference = 0.0 for i in range(7, 14): system.part[0].pos = [i, 0, 0] system.integrator.run(0) # Check Force expected_force = -2 * math.pi * bjerrum_length particle_force = system.part[0].f if abs(expected_force - particle_force[0]) > force_difference: force_difference = abs(expected_force - particle_force[0]) print("Force deviation: {}".format(force_difference)) self.assertLess( force_difference, 1.0e-04, "Force accuracy in X not achieved, allowed deviation: " "1.0e-04, measured: {}".format(force_difference)) # Unset species for i in range(int(box_y / agrid)): for j in range(int(box_z / agrid)): positive_ions[10, i, j].density = 0.0 negative_ions[30, i, j].density = 0.0 ################################################################## # Y # Setup EK species for i in range(int(box_x / agrid)): for j in range(int(box_z / agrid)): positive_ions[i, 10, j].density = 1.0 / agrid negative_ions[i, 30, j].density = 1.0 / agrid #Setup MD particle and integrate force_difference = 0.0 for i in range(7, 14): system.part[0].pos = [0, i, 0] system.integrator.run(0) # Check Force expected_force = -2 * math.pi * bjerrum_length particle_force = system.part[0].f if abs(expected_force - particle_force[1]) > force_difference: force_difference = abs(expected_force - particle_force[1]) print("Force deviation: {}".format(force_difference)) self.assertLess( force_difference, 1.0e-04, "Force accuracy in Y not achieved, allowed deviation: " "1.0e-04, measured: {}".format(force_difference)) # Unset species for i in range(int(box_x / agrid)): for j in range(int(box_z / agrid)): positive_ions[i, 10, j].density = 0.0 negative_ions[i, 30, j].density = 0.0 ################################################################## # Y # Setup EK species for i in range(int(box_x / agrid)): for j in range(int(box_y / agrid)): positive_ions[i, j, 10].density = 1.0 / agrid negative_ions[i, j, 30].density = 1.0 / agrid # Setup MD particle and integrate force_difference = 0.0 for i in range(7, 14): system.part[0].pos = [0, 0, i] system.integrator.run(0) # Check Force expected_force = -2 * math.pi * bjerrum_length particle_force = system.part[0].f if abs(expected_force - particle_force[2]) > force_difference: force_difference = abs(expected_force - particle_force[2]) print("Force deviation: {}".format(force_difference)) self.assertLess( force_difference, 1.0e-04, "Force accuracy in Z not achieved, allowed deviation: " "1.0e-04, measured: {}".format(force_difference)) # Unset species for i in range(int(box_x / agrid)): for j in range(int(box_y / agrid)): positive_ions[i, j, 10].density = 0.0 negative_ions[i, j, 30].density = 0.0