class MagnetostaticsInteractionsTests(ut.TestCase): # Handle to espresso system system = espressomd.System(box_l=[1.0, 1.0, 1.0]) def setUp(self): self.system.box_l = [10, 10, 10] if not self.system.part.exists(0): self.system.part.add(id=0, pos=(0.1, 0.1, 0.1), dip=(1.3, 2.1, -6)) if not self.system.part.exists(1): self.system.part.add(id=1, pos=(0, 0, 0), dip=(7.3, 6.1, -4)) if espressomd.has_features(["DP3M"]): test_DP3M = generate_test_for_class( system, magnetostatics.DipolarP3M, dict(prefactor=1.0, epsilon=0.0, inter=1000, mesh_off=[0.5, 0.5, 0.5], r_cut=2.4, mesh=[8, 8, 8], cao=1, alpha=12, accuracy=0.01, tune=False)) if espressomd.has_features(["DIPOLAR_DIRECT_SUM"]): test_DdsCpu = generate_test_for_class( system, magnetostatics.DipolarDirectSumCpu, dict(prefactor=3.4)) if espressomd.has_features("EXPERIMENTAL_FEATURES"): test_DdsRCpu = generate_test_for_class( system, magnetostatics.DipolarDirectSumWithReplicaCpu, dict(prefactor=3.4, n_replica=2))
def test_dh(self): dh_params = dict(prefactor=1.2, kappa=0.8, r_cut=2.0) test_DH = tests_common.generate_test_for_class(self.system, electrostatics.DH, dh_params) dh = espressomd.electrostatics.DH(prefactor=dh_params['prefactor'], kappa=dh_params['kappa'], r_cut=dh_params['r_cut']) self.system.actors.add(dh) dr = 0.001 r = np.arange(.5, 1.01 * dh_params['r_cut'], dr) u_dh = self.calc_dh_potential(r, dh_params) f_dh = -np.gradient(u_dh, dr) # zero the discontinuity, and re-evaluate the derivitive as a backwards # difference i_cut = np.argmin((dh_params['r_cut'] - r)**2) f_dh[i_cut] = 0 f_dh[i_cut - 1] = (u_dh[i_cut - 2] - u_dh[i_cut - 1]) / dr u_dh_core = np.zeros_like(r) f_dh_core = np.zeros_like(r) # need to update forces for i, ri in enumerate(r): self.system.part[1].pos = self.system.part[0].pos + [ri, 0, 0] self.system.integrator.run(0) u_dh_core[i] = self.system.analysis.energy()['coulomb'] f_dh_core[i] = self.system.part[0].f[0] np.testing.assert_allclose(u_dh_core, u_dh, atol=1e-7) np.testing.assert_allclose(f_dh_core, -f_dh, atol=1e-2) self.system.actors.remove(dh)
def test_p3m(self): self.system.part[0].pos = [1.0, 2.0, 2.0] self.system.part[1].pos = [3.0, 2.0, 2.0] # results, p3m_energy = -0.501062398379 p3m_force = 2.48921612e-01 test_P3M = tests_common.generate_test_for_class( self.system, electrostatics.P3M, dict(accuracy=9.910945054074526e-08, mesh=[22, 22, 22], cao=7, r_cut=8.906249999999998, alpha=0.387611049779351, tune=False)) p3m = espressomd.electrostatics.P3M(prefactor=1.0, accuracy=9.910945054074526e-08, mesh=[22, 22, 22], cao=7, r_cut=8.906249999999998, alpha=0.387611049779351, tune=False) self.system.actors.add(p3m) self.assertAlmostEqual(self.system.analysis.energy()['coulomb'], p3m_energy) # need to update forces self.system.integrator.run(0) np.testing.assert_allclose(np.copy(self.system.part[0].f), [p3m_force, 0, 0], atol=1E-5) np.testing.assert_allclose(np.copy(self.system.part[1].f), [-p3m_force, 0, 0], atol=1E-10) self.system.actors.remove(p3m)
class MagnetostaticsInterface(ut.TestCase): system = espressomd.System(box_l=[10., 10., 10.]) def setUp(self): self.system.box_l = [10., 10., 10.] self.system.part.add(pos=(0.0, 0.0, 0.0), dip=(1.3, 2.1, -6)) self.system.part.add(pos=(0.1, 0.1, 0.1), dip=(7.3, 6.1, -4)) def tearDown(self): self.system.part.clear() self.system.actors.clear() if espressomd.has_features("DIPOLES"): test_dds_cpu = tests_common.generate_test_for_class( system, espressomd.magnetostatics.DipolarDirectSumCpu, dict(prefactor=3.4)) if espressomd.has_features( "DIPOLAR_DIRECT_SUM") and espressomd.gpu_available(): test_dds_gpu = tests_common.generate_test_for_class( system, espressomd.magnetostatics.DipolarDirectSumGpu, dict(prefactor=3.4)) if espressomd.has_features("DIPOLES"): test_dds_replica = tests_common.generate_test_for_class( system, espressomd.magnetostatics.DipolarDirectSumWithReplicaCpu, dict(prefactor=3.4, n_replica=2)) def test_exceptions(self): actor = espressomd.magnetostatics.DipolarDirectSumCpu(prefactor=-1) with self.assertRaises(ValueError): self.system.actors.add(actor) actor = self.system.actors[0] actor.set_params(prefactor=1) with self.assertRaises(ValueError): actor.set_params(prefactor=-1) with self.assertRaises(ValueError): actor.set_magnetostatics_prefactor()
def test_rf(self): """Tests the ReactionField coulomb interaction by comparing the potential and force against the analytic values""" rf_params = dict(prefactor=1.0, kappa=2.0, epsilon1=1.0, epsilon2=2.0, r_cut=2.0) test_RF = tests_common.generate_test_for_class( self.system, electrostatics.ReactionField, rf_params) rf = espressomd.electrostatics.ReactionField( prefactor=rf_params['prefactor'], kappa=rf_params['kappa'], epsilon1=rf_params['epsilon1'], epsilon2=rf_params['epsilon2'], r_cut=rf_params['r_cut']) self.system.actors.add(rf) dr = 0.001 r = np.arange(.5, 1.01 * rf_params['r_cut'], dr) u_rf = self.calc_rf_potential(r, rf_params) f_rf = -np.gradient(u_rf, dr) # zero the discontinuity, and re-evaluate the derivitive as a backwards # difference i_cut = np.argmin((rf_params['r_cut'] - r)**2) f_rf[i_cut] = 0 f_rf[i_cut - 1] = (u_rf[i_cut - 2] - u_rf[i_cut - 1]) / dr u_rf_core = np.zeros_like(r) f_rf_core = np.zeros_like(r) for i, ri in enumerate(r): self.system.part[1].pos = self.system.part[0].pos + [ri, 0, 0] self.system.integrator.run(0) u_rf_core[i] = self.system.analysis.energy()['coulomb'] f_rf_core[i] = self.system.part[0].f[0] np.testing.assert_allclose(u_rf_core, u_rf, atol=1e-7) np.testing.assert_allclose(f_rf_core, -f_rf, atol=1e-2) self.system.actors.remove(rf)
class MagnetostaticsP3M(ut.TestCase): system = espressomd.System(box_l=3 * [10.]) def setUp(self): self.partcls = self.system.part.add(pos=[[4.0, 2.0, 2.0], [6.0, 2.0, 2.0]], dip=[(1.3, 2.1, -6.0), (7.3, 6.1, -4.0)]) def tearDown(self): self.system.part.clear() self.system.actors.clear() if espressomd.has_features("DP3M"): test_DP3M = tests_common.generate_test_for_class( system, espressomd.magnetostatics.DipolarP3M, dict(prefactor=1., epsilon=0., mesh_off=[0.5, 0.5, 0.5], r_cut=2.4, cao=1, mesh=[8, 8, 8], alpha=12, accuracy=0.01, tune=False)) def test_dp3m(self): self.system.time_step = 0.01 prefactor = 1.1 box_vol = self.system.volume() p1, p2 = self.partcls dip = np.copy(p1.dip + p2.dip) dp3m_params = { 'accuracy': 1e-6, 'mesh': [49, 49, 49], 'cao': 7, 'r_cut': 4.739799499511719, 'alpha': 0.9056147262573242 } mdlc_params = {'maxPWerror': 1e-5, 'gap_size': 5.} # reference values for energy and force calculated for prefactor = 1.1 ref_dp3m_energy = 1.673333 ref_dp3m_force = np.array([-3.54175042, -4.6761059, 9.96632774]) ref_dp3m_torque1 = np.array([-3.29316117, -13.21245739, -5.33787892]) ref_dp3m_torque2 = np.array([3.98103932, -7.47123148, -4.12823244]) # check metallic case dp3m = espressomd.magnetostatics.DipolarP3M(prefactor=prefactor, epsilon='metallic', tune=False, **dp3m_params) self.system.actors.add(dp3m) self.system.integrator.run(0, recalc_forces=True) energy = self.system.analysis.energy()['dipolar'] tol = 1e-5 np.testing.assert_allclose(energy, ref_dp3m_energy, atol=tol) np.testing.assert_allclose(np.copy(p1.f), ref_dp3m_force, atol=tol) np.testing.assert_allclose(np.copy(p2.f), -ref_dp3m_force, atol=tol) np.testing.assert_allclose(np.copy( p1.convert_vector_space_to_body(p1.torque_lab)), ref_dp3m_torque1, atol=tol) np.testing.assert_allclose(np.copy( p2.convert_vector_space_to_body(p2.torque_lab)), ref_dp3m_torque2, atol=tol) # keep current values as reference to check for DP3M dipole correction ref_dp3m_energy_metallic = self.system.analysis.energy()['dipolar'] ref_dp3m_forces_metallic = np.copy(self.partcls.f) ref_dp3m_torque_metallic = np.array([ p1.convert_vector_space_to_body(p1.torque_lab), p2.convert_vector_space_to_body(p2.torque_lab) ]) # MDLC cancels out dipole correction mdlc = espressomd.magnetostatic_extensions.DLC(**mdlc_params) self.system.actors.add(mdlc) # keep current values as reference to check for MDLC dipole correction self.system.integrator.run(0, recalc_forces=True) ref_mdlc_energy_metallic = self.system.analysis.energy()['dipolar'] ref_mdlc_forces_metallic = np.copy(self.partcls.f) ref_mdlc_torque_metallic = np.copy(self.partcls.torque_lab) self.system.actors.clear() # check non-metallic case tol = 1e-10 for epsilon in np.power(10., np.arange(-4, 5)): dipole_correction = 4 * np.pi / box_vol / (1 + 2 * epsilon) e_correction = dipole_correction / 2 * np.linalg.norm(dip)**2 t_correction = np.cross([p1.dip, p2.dip], dipole_correction * dip) ref_dp3m_energy = ref_dp3m_energy_metallic + prefactor * e_correction ref_dp3m_forces = ref_dp3m_forces_metallic ref_dp3m_torque = ref_dp3m_torque_metallic - prefactor * t_correction dp3m = espressomd.magnetostatics.DipolarP3M(prefactor=prefactor, epsilon=epsilon, tune=False, **dp3m_params) self.system.actors.add(dp3m) self.system.integrator.run(0, recalc_forces=True) dp3m_forces = np.copy(self.partcls.f) dp3m_torque = np.array([ p1.convert_vector_space_to_body(p1.torque_lab), p2.convert_vector_space_to_body(p2.torque_lab) ]) dp3m_energy = self.system.analysis.energy()['dipolar'] np.testing.assert_allclose(dp3m_forces, ref_dp3m_forces, atol=tol) np.testing.assert_allclose(dp3m_torque, ref_dp3m_torque, atol=tol) np.testing.assert_allclose(dp3m_energy, ref_dp3m_energy, atol=tol) # MDLC cancels out dipole correction ref_mdlc_energy = ref_mdlc_energy_metallic ref_mdlc_forces = ref_mdlc_forces_metallic ref_mdlc_torque = ref_mdlc_torque_metallic mdlc = espressomd.magnetostatic_extensions.DLC(**mdlc_params) self.system.actors.add(mdlc) self.system.integrator.run(0, recalc_forces=True) mdlc_forces = np.copy(self.partcls.f) mdlc_torque = np.copy(self.partcls.torque_lab) mdlc_energy = self.system.analysis.energy()['dipolar'] np.testing.assert_allclose(mdlc_forces, ref_mdlc_forces, atol=tol) np.testing.assert_allclose(mdlc_torque, ref_mdlc_torque, atol=tol) np.testing.assert_allclose(mdlc_energy, ref_mdlc_energy, atol=tol) self.system.actors.clear()
class MagnetostaticsInteractionsTests(ut.TestCase): # Handle to espresso system system = espressomd.System(box_l=[10., 10., 10.]) def setUp(self): self.system.box_l = [10., 10., 10.] self.system.part.add(id=0, pos=(0.1, 0.1, 0.1), dip=(1.3, 2.1, -6)) self.system.part.add(id=1, pos=(0, 0, 0), dip=(7.3, 6.1, -4)) def tearDown(self): self.system.part.clear() self.system.actors.clear() if espressomd.has_features(["DP3M"]): test_DP3M = generate_test_for_class( system, magnetostatics.DipolarP3M, dict(prefactor=1., epsilon=0., mesh_off=[0.5, 0.5, 0.5], r_cut=2.4, cao=1, mesh=[8, 8, 8], alpha=12, accuracy=0.01, tune=False)) if espressomd.has_features(["DIPOLAR_DIRECT_SUM"]): test_DdsCpu = generate_test_for_class( system, magnetostatics.DipolarDirectSumCpu, dict(prefactor=3.4)) if espressomd.has_features("EXPERIMENTAL_FEATURES"): test_DdsRCpu = generate_test_for_class( system, magnetostatics.DipolarDirectSumWithReplicaCpu, dict(prefactor=3.4, n_replica=2)) def ref_values(self, epsilon=np.inf): x = 1. / (1 + 2 * epsilon) dp3m_energy = 1.66706 * x + 1.673333 dp3m_torque1 = np.array([-0.5706503 * x + 2.561371, -0.1812375 * x + 10.394144, -0.2976916 * x + 9.965342]) dp3m_torque2 = np.array([+0.3362938 * x + 1.854679, -0.2269749 * x - 3.638175, +0.5315054 * x + 8.487292]) dp3m_force = np.array([-3.54175042, -4.6761059, 9.96632774]) alpha, r_cut, mesh, cao = (9.056147262573242, 4.739799499511719, 49, 7) dp3m_params = {'prefactor': 1.1, 'accuracy': 9.995178689932661e-07, 'mesh': mesh, 'mesh_off': [0.5, 0.5, 0.5], 'cao': cao, 'additional_mesh': [0.0, 0.0, 0.0], 'alpha': alpha / 10, 'alpha_L': alpha, 'r_cut': r_cut, 'r_cut_iL': r_cut / self.system.box_l[0], 'cao_cut': 3 * [self.system.box_l[0] / mesh / 2 * cao], 'a': 3 * [self.system.box_l[0] / mesh]} return dp3m_params, dp3m_energy, dp3m_force, dp3m_torque1, dp3m_torque2 @utx.skipIfMissingFeatures(["DP3M"]) def test_dp3m(self): self.system.time_step = 0.01 self.system.part[0].pos = [1.0, 2.0, 2.0] self.system.part[1].pos = [3.0, 2.0, 2.0] dp3m_params, dp3m_energy, dp3m_force, dp3m_torque1, dp3m_torque2 = self.ref_values() dp3m = espressomd.magnetostatics.DipolarP3M(tune=False, **dp3m_params) self.system.actors.add(dp3m) self.assertAlmostEqual(self.system.analysis.energy()['dipolar'], dp3m_energy, places=5) # update forces and torques self.system.integrator.run(0) np.testing.assert_allclose(np.copy(self.system.part[0].f), dp3m_force, atol=1E-5) np.testing.assert_allclose(np.copy(self.system.part[1].f), -dp3m_force, atol=1E-5) np.testing.assert_allclose(np.copy(self.system.part[0].torque_lab), dp3m_torque1, atol=1E-5) np.testing.assert_allclose(np.copy(self.system.part[1].torque_lab), dp3m_torque2, atol=1E-5) @utx.skipIfMissingFeatures(["DP3M"]) def test_dp3m_non_metallic(self): self.system.time_step = 0.01 self.system.part[0].pos = [1.0, 2.0, 2.0] self.system.part[1].pos = [3.0, 2.0, 2.0] for epsilon_power in range(-4, 5): epsilon = 10**epsilon_power dp3m_params, dp3m_energy, dp3m_force, dp3m_torque1, dp3m_torque2 = self.ref_values( epsilon) dp3m = espressomd.magnetostatics.DipolarP3M( tune=False, epsilon=epsilon, **dp3m_params) self.system.actors.add(dp3m) self.assertAlmostEqual(self.system.analysis.energy()['dipolar'], dp3m_energy, places=5) # update forces and torques self.system.integrator.run(0) np.testing.assert_allclose(np.copy(self.system.part[0].f), dp3m_force, atol=1E-5) np.testing.assert_allclose(np.copy(self.system.part[1].f), -dp3m_force, atol=1E-5) np.testing.assert_allclose(np.copy(self.system.part[0].torque_lab), dp3m_torque1, atol=1E-5) np.testing.assert_allclose(np.copy(self.system.part[1].torque_lab), dp3m_torque2, atol=1E-5) self.system.actors.remove(dp3m)
class MagnetostaticsInterface(ut.TestCase): system = espressomd.System(box_l=[10., 10., 10.]) def setUp(self): self.system.box_l = [10., 10., 10.] self.system.periodicity = [True, True, True] self.system.part.add(pos=(0.0, 0.0, 0.0), dip=(1.3, 2.1, -6)) self.system.part.add(pos=(0.1, 0.1, 0.1), dip=(7.3, 6.1, -4)) def tearDown(self): self.system.part.clear() self.system.actors.clear() if espressomd.has_features("DIPOLES"): test_dds_cpu = tests_common.generate_test_for_class( system, espressomd.magnetostatics.DipolarDirectSumCpu, dict(prefactor=3.4)) if espressomd.has_features( "DIPOLAR_DIRECT_SUM") and espressomd.gpu_available(): test_dds_gpu = tests_common.generate_test_for_class( system, espressomd.magnetostatics.DipolarDirectSumGpu, dict(prefactor=3.4)) if espressomd.has_features("DIPOLES"): test_dds_replica = tests_common.generate_test_for_class( system, espressomd.magnetostatics.DipolarDirectSumWithReplicaCpu, dict(prefactor=3.4, n_replica=2)) def test_exceptions(self): actor = espressomd.magnetostatics.DipolarDirectSumCpu(prefactor=-1) with self.assertRaises(ValueError): self.system.actors.add(actor) actor = self.system.actors[0] actor.set_params(prefactor=1) with self.assertRaises(ValueError): actor.set_params(prefactor=-1) with self.assertRaises(ValueError): actor.set_magnetostatics_prefactor() self.system.actors.clear() actor_dawaanr = espressomd.magnetostatics.DipolarDirectSumCpu( prefactor=1) actor_mdlc = espressomd.magnetostatic_extensions.DLC( gap_size=2, maxPWerror=1e-5) self.system.actors.add(actor_dawaanr) with self.assertRaisesRegex(RuntimeError, 'MDLC cannot extend the currently active magnetostatics solver'): self.system.actors.add(actor_mdlc) self.system.actors.clear() actor = espressomd.magnetostatics.DipolarDirectSumWithReplicaCpu( prefactor=1, n_replica=-2) with self.assertRaisesRegex(RuntimeError, 'requires n_replica >= 0'): self.system.actors.add(actor) self.system.actors.clear() actor = espressomd.magnetostatics.DipolarDirectSumWithReplicaCpu( prefactor=1, n_replica=0) with self.assertRaisesRegex(RuntimeError, 'with replica does not support a periodic system with zero replica'): self.system.actors.add(actor) self.system.actors.clear() self.system.periodicity = [True, True, False] actor = espressomd.magnetostatics.DipolarDirectSumWithReplicaCpu( prefactor=1, n_replica=1) solver_mdlc = espressomd.magnetostatic_extensions.DLC( gap_size=1, maxPWerror=1e-5) self.system.actors.add(actor) with self.assertRaisesRegex(RuntimeError, "MDLC requires periodicity 1 1 1"): self.system.actors.add(solver_mdlc) self.system.actors.remove(solver_mdlc) self.system.periodicity = [True, True, True] self.system.box_l = [10., 10. + 2e-3, 10.] with self.assertRaisesRegex(RuntimeError, "box size in x direction is different from y direction"): self.system.actors.add(solver_mdlc) self.system.actors.clear() self.system.box_l = [10., 10., 10.]