def test_biotsavart_coil_current_taylortest(self):
        coil0 = get_coil()
        current0 = 1e4
        coil1 = get_coil(perturb=True)
        current1 = 1e3
        bs = BiotSavart([coil0, coil1], [current0, current1])
        points = np.asarray(
            17 * [[-1.41513202e-03, 8.99999382e-01, -3.14473221e-04]])
        bs.set_points(points)
        B = bs.B()
        J = bs.dB_by_dX()
        H = bs.d2B_by_dXdX()
        dB = bs.dB_by_dcoilcurrents()
        dJ = bs.d2B_by_dXdcoilcurrents()
        dH = bs.d3B_by_dXdXdcoilcurrents()

        h = 1.
        bs.currents_optim[0].set_dofs(1e4 + h)
        bs.invalidate_cache()
        Bp = bs.B()
        Jp = bs.dB_by_dX()
        Hp = bs.d2B_by_dXdX()
        bs.currents_optim[0].set_dofs(1e4 - h)
        bs.invalidate_cache()
        Bm = bs.B()
        Jm = bs.dB_by_dX()
        Hm = bs.d2B_by_dXdX()
        dB_approx = (Bp - Bm) / (2 * h)
        dJ_approx = (Jp - Jm) / (2 * h)
        dH_approx = (Hp - Hm) / (2 * h)
        assert np.linalg.norm(dB[0] - dB_approx) < 1e-15
        assert np.linalg.norm(dJ[0] - dJ_approx) < 1e-15
        assert np.linalg.norm(dH[0] - dH_approx) < 1e-13
    def subtest_biotsavart_d2B_by_dXdX_taylortest(self, idx):
        coil = get_coil()
        bs = BiotSavart([coil], [1e4])
        points = np.asarray(
            17 * [[-1.41513202e-03, 8.99999382e-01, -3.14473221e-04]])
        bs.set_points(points)
        dB_by_dX, d2B_by_dXdX = bs.dB_by_dX(), bs.d2B_by_dXdX()
        for d1 in range(3):
            for d2 in range(3):
                second_deriv = d2B_by_dXdX[idx, d1, d2]
                err = 1e6
                for i in range(5, 10):
                    eps = 0.5**i

                    ed2 = np.zeros((1, 3))
                    ed2[0, d2] = 1.

                    bs.set_points(points + eps * ed2)
                    dB_dXp = bs.dB_by_dX()[idx, d1]

                    bs.set_points(points - eps * ed2)
                    dB_dXm = bs.dB_by_dX()[idx, d1]

                    second_deriv_est = (dB_dXp - dB_dXm) / (2. * eps)

                    new_err = np.linalg.norm(second_deriv - second_deriv_est)
                    assert new_err < 0.30 * err
                    err = new_err
    def test_dBdX_by_dcoilcoeff_reverse_taylortest(self):
        np.random.seed(1)
        coil = get_coil()
        bs = BiotSavart([coil], [1e4])
        points = np.asarray(
            17 * [[-1.41513202e-03, 8.99999382e-01, -3.14473221e-04]])
        points += 0.001 * (np.random.rand(*points.shape) - 0.5)

        bs.set_points(points)
        coil_dofs = np.asarray(coil.get_dofs())
        B = bs.B()
        dBdX = bs.dB_by_dX()
        J0 = np.sum(dBdX**2)
        dJ = bs.B_and_dB_vjp(B, dBdX)

        h = 1e-2 * np.random.rand(len(coil_dofs)).reshape(coil_dofs.shape)
        dJ_dh = 2 * np.sum(dJ[1][0] * h)
        err = 1e6
        for i in range(5, 10):
            eps = 0.5**i
            coil.set_dofs(coil_dofs + eps * h)
            bs.clear_cached_properties()
            dBdXh = bs.dB_by_dX()
            Jh = np.sum(dBdXh**2)
            deriv_est = (Jh - J0) / eps
            err_new = np.linalg.norm(deriv_est - dJ_dh)
            assert err_new < 0.55 * err
            err = err_new
 def subtest_biotsavart_gradient_symmetric_and_divergence_free(self, idx):
     coil = get_coil()
     bs = BiotSavart([coil], [1e4])
     points = np.asarray(
         17 * [[-1.41513202e-03, 8.99999382e-01, -3.14473221e-04]])
     points += 0.001 * (np.random.rand(*points.shape) - 0.5)
     bs.set_points(points)
     dB = bs.dB_by_dX()
     assert abs(dB[idx][0, 0] + dB[idx][1, 1] + dB[idx][2, 2]) < 1e-14
     assert np.allclose(dB[idx], dB[idx].T)
Beispiel #5
0
 def test_helicalcoil_Bfield(self):
     point = [[-1.41513202e-03, 8.99999382e-01, -3.14473221e-04]]
     field = [[-0.00101961, 0.20767292, -0.00224908]]
     derivative = [[[0.47545098, 0.01847397, 1.10223595],
                    [0.01847426, -2.66700072, 0.01849548],
                    [1.10237535, 0.01847085, 2.19154973]]]
     coils = [CurveHelical(100, 2, 5, 2, 1., 0.3) for i in range(2)]
     coils[0].set_dofs(np.concatenate(([0, 0], [0, 0])))
     coils[1].set_dofs(np.concatenate(([np.pi / 2, 0], [0, 0])))
     currents = [-3.07e5, 3.07e5]
     Bhelical = BiotSavart(coils, currents)
     Bhelical.set_points(point)
     assert np.allclose(Bhelical.B(), field)
     assert np.allclose(Bhelical.dB_by_dX(), derivative)
Beispiel #6
0
    def test_sum_Bfields(self):
        pointVar = 1e-1
        npoints = 20
        points = np.asarray(
            npoints * [[-1.41513202e-03, 8.99999382e-01, -3.14473221e-04]])
        points += pointVar * (np.random.rand(*points.shape) - 0.5)
        # Set up helical field
        coils = [CurveHelical(101, 2, 5, 2, 1., 0.3) for i in range(2)]
        coils[0].set_dofs(np.concatenate(([np.pi / 2, 0], [0, 0])))
        coils[1].set_dofs(np.concatenate(([0, 0], [0, 0])))
        currents = [-2.1e5, 2.1e5]
        Bhelical = BiotSavart(coils, currents)
        # Set up toroidal fields
        Btoroidal1 = ToroidalField(1., 1.)
        Btoroidal2 = ToroidalField(1.2, 0.1)
        # Set up sum of the three in two different ways
        Btotal1 = MagneticFieldSum([Bhelical, Btoroidal1, Btoroidal2])
        Btotal2 = Bhelical + Btoroidal1 + Btoroidal2
        Btotal3 = Btoroidal1 + Btoroidal2
        # Evaluate at a given point
        Bhelical.set_points(points)
        Btoroidal1.set_points(points)
        Btoroidal2.set_points(points)
        Btotal1.set_points(points)
        Btotal2.set_points(points)
        Btotal3.set_points(points)
        # Verify
        assert np.allclose(Btotal1.B(), Btotal2.B())
        assert np.allclose(Bhelical.B() + Btoroidal1.B() + Btoroidal2.B(),
                           Btotal1.B())
        assert np.allclose(Btotal1.dB_by_dX(), Btotal2.dB_by_dX())
        assert np.allclose(
            Bhelical.dB_by_dX() + Btoroidal1.dB_by_dX() +
            Btoroidal2.dB_by_dX(), Btotal1.dB_by_dX())

        assert np.allclose(Btoroidal1.d2B_by_dXdX() + Btoroidal2.d2B_by_dXdX(),
                           Btotal3.d2B_by_dXdX())
        assert np.allclose(Btoroidal1.A() + Btoroidal2.A(), Btotal3.A())
        assert np.allclose(Btoroidal1.dA_by_dX() + Btoroidal2.dA_by_dX(),
                           Btotal3.dA_by_dX())
        assert np.allclose(Btoroidal1.d2A_by_dXdX() + Btoroidal2.d2A_by_dXdX(),
                           Btotal3.d2A_by_dXdX())
 def subtest_biotsavart_dBdX_taylortest(self, idx):
     coil = get_coil()
     bs = BiotSavart([coil], [1e4])
     points = np.asarray(
         17 * [[-1.41513202e-03, 8.99999382e-01, -3.14473221e-04]])
     points += 0.001 * (np.random.rand(*points.shape) - 0.5)
     bs.set_points(points)
     B0 = bs.B()[idx]
     dB = bs.dB_by_dX()[idx]
     for direction in [
             np.asarray((1., 0, 0)),
             np.asarray((0, 1., 0)),
             np.asarray((0, 0, 1.))
     ]:
         deriv = dB.T.dot(direction)
         err = 1e6
         for i in range(5, 10):
             eps = 0.5**i
             bs.set_points(points + eps * direction)
             Beps = bs.B()[idx]
             deriv_est = (Beps - B0) / (eps)
             new_err = np.linalg.norm(deriv - deriv_est)
             assert new_err < 0.55 * err
             err = new_err
Beispiel #8
0
 def test_circularcoil_Bfield(self):
     current = 1.2e7
     radius = 1.12345
     center = [0.12345, 0.6789, 1.23456]
     pointVar = 1e-1
     npoints = 1
     ## verify the field at the center of a coil in the xy plane
     Bfield = CircularCoil(I=current, r0=radius)
     points = np.array([[1e-10, 0, 0.]])
     Bfield.set_points(points)
     assert np.allclose(Bfield.B(),
                        [[0, 0, current / 1e7 * 2 * np.pi / radius]])
     # Verify that divergence is zero
     dB1_by_dX = Bfield.dB_by_dX()
     assert np.allclose(
         dB1_by_dX[:, 0, 0] + dB1_by_dX[:, 1, 1] + dB1_by_dX[:, 2, 2],
         np.zeros((npoints)))
     # Verify that, as a vacuum field, grad B=grad grad phi so that grad_i B_j = grad_j B_i
     transpGradB1 = [dBdx.T for dBdx in dB1_by_dX]
     assert np.allclose(dB1_by_dX, transpGradB1)
     ### compare to biosavart(circular_coil)
     ## at these points
     points = np.asarray(
         npoints * [[-1.41513202e-03, 8.99999382e-01, -3.14473221e-04]])
     points += pointVar * (np.random.rand(*points.shape) - 0.5)
     ## verify with a x^2+z^2=radius^2 circular coil
     normal = [np.pi / 2, 0]
     coils = [CurveXYZFourier(300, 1)]
     coils[0].set_dofs(
         [center[0], radius, 0., center[1], 0., 0., center[2], 0., radius])
     Bcircular = BiotSavart(coils, [current])
     Bfield = CircularCoil(I=current,
                           r0=radius,
                           normal=normal,
                           center=center)
     Bfield.set_points(points)
     Bcircular.set_points(points)
     dB1_by_dX = Bfield.dB_by_dX()
     transpGradB1 = [dBdx.T for dBdx in dB1_by_dX]
     assert np.allclose(Bfield.B(), Bcircular.B())
     assert np.allclose(Bfield.dB_by_dX(), Bcircular.dB_by_dX())
     assert np.allclose(
         dB1_by_dX[:, 0, 0] + dB1_by_dX[:, 1, 1] + dB1_by_dX[:, 2, 2],
         np.zeros((npoints)))
     assert np.allclose(dB1_by_dX, transpGradB1)
     # use normal = [0, 1, 0]
     normal = [0, 1, 0]
     coils = [CurveXYZFourier(300, 1)]
     coils[0].set_dofs(
         [center[0], radius, 0., center[1], 0., 0., center[2], 0., radius])
     Bcircular = BiotSavart(coils, [current])
     Bfield = CircularCoil(I=current,
                           r0=radius,
                           normal=normal,
                           center=center)
     Bfield.set_points(points)
     Bcircular.set_points(points)
     dB1_by_dX = Bfield.dB_by_dX()
     transpGradB1 = [dBdx.T for dBdx in dB1_by_dX]
     assert np.allclose(Bfield.B(), Bcircular.B())
     assert np.allclose(Bfield.dB_by_dX(), Bcircular.dB_by_dX())
     assert np.allclose(
         dB1_by_dX[:, 0, 0] + dB1_by_dX[:, 1, 1] + dB1_by_dX[:, 2, 2],
         np.zeros((npoints)))
     assert np.allclose(dB1_by_dX, transpGradB1)
     ## verify with a y^2+z^2=radius^2 circular coil
     normal = [np.pi / 2, np.pi / 2]
     coils = [CurveXYZFourier(300, 1)]
     coils[0].set_dofs(
         [center[0], 0, 0., center[1], radius, 0., center[2], 0., radius])
     Bcircular = BiotSavart(coils, [current])
     Bfield = CircularCoil(I=current,
                           r0=radius,
                           normal=normal,
                           center=center)
     Bfield.set_points(points)
     Bcircular.set_points(points)
     dB1_by_dX = Bfield.dB_by_dX()
     transpGradB1 = [dBdx.T for dBdx in dB1_by_dX]
     assert np.allclose(Bfield.B(), Bcircular.B())
     assert np.allclose(Bfield.dB_by_dX(), Bcircular.dB_by_dX())
     assert np.allclose(dB1_by_dX[:, 0, 0] +
                        dB1_by_dX[:, 1, 1] + dB1_by_dX[:, 2, 2],
                        np.zeros((npoints)))  # divergence
     assert np.allclose(dB1_by_dX, transpGradB1)  # symmetry of the gradient
     Bfield.set_points([[0.1, 0.2, 0.3]])
     Afield = Bfield.A()
     assert np.allclose(Afield, [[0, 5.15786, -2.643056]])
     # use normal=[1,0,0]
     normal = [1, 0, 0]
     coils = [CurveXYZFourier(300, 1)]
     coils[0].set_dofs(
         [center[0], 0, 0., center[1], radius, 0., center[2], 0., radius])
     Bcircular = BiotSavart(coils, [current])
     Bfield = CircularCoil(I=current,
                           r0=radius,
                           normal=normal,
                           center=center)
     Bfield.set_points(points)
     Bcircular.set_points(points)
     dB1_by_dX = Bfield.dB_by_dX()
     transpGradB1 = [dBdx.T for dBdx in dB1_by_dX]
     assert np.allclose(Bfield.B(), Bcircular.B())
     assert np.allclose(Bfield.dB_by_dX(), Bcircular.dB_by_dX())
     assert np.allclose(dB1_by_dX[:, 0, 0] +
                        dB1_by_dX[:, 1, 1] + dB1_by_dX[:, 2, 2],
                        np.zeros((npoints)))  # divergence
     assert np.allclose(dB1_by_dX, transpGradB1)  # symmetry of the gradient
     ## verify with a x^2+y^2=radius^2 circular coil
     center = [0, 0, 0]
     normal = [0, 0]
     coils = [CurveXYZFourier(300, 1)]
     coils[0].set_dofs(
         [center[0], 0, radius, center[1], radius, 0., center[2], 0., 0.])
     Bcircular = BiotSavart(coils, [current])
     coils2 = [CurveRZFourier(300, 1, 1, True)]
     coils2[0].set_dofs([radius, 0, 0])
     Bcircular2 = BiotSavart(coils, [current])
     Bfield = CircularCoil(I=current,
                           r0=radius,
                           normal=normal,
                           center=center)
     Bfield.set_points(points)
     Bcircular.set_points(points)
     Bcircular2.set_points(points)
     dB1_by_dX = Bfield.dB_by_dX()
     transpGradB1 = [dBdx.T for dBdx in dB1_by_dX]
     assert np.allclose(Bfield.B(), Bcircular.B())
     assert np.allclose(Bfield.B(), Bcircular2.B())
     assert np.allclose(Bfield.dB_by_dX(), Bcircular.dB_by_dX())
     assert np.allclose(Bfield.dB_by_dX(), Bcircular2.dB_by_dX())
     assert np.allclose(dB1_by_dX[:, 0, 0] +
                        dB1_by_dX[:, 1, 1] + dB1_by_dX[:, 2, 2],
                        np.zeros((npoints)))  # divergence
     assert np.allclose(dB1_by_dX, transpGradB1)  # symmetry of the gradient
     # use normal = [0, 0, 1]
     center = [0, 0, 0]
     normal = [0, 0, 1]
     coils = [CurveXYZFourier(300, 1)]
     coils[0].set_dofs(
         [center[0], 0, radius, center[1], radius, 0., center[2], 0., 0.])
     Bcircular = BiotSavart(coils, [current])
     coils2 = [CurveRZFourier(300, 1, 1, True)]
     coils2[0].set_dofs([radius, 0, 0])
     Bcircular2 = BiotSavart(coils, [current])
     Bfield = CircularCoil(I=current,
                           r0=radius,
                           normal=normal,
                           center=center)
     Bfield.set_points(points)
     Bcircular.set_points(points)
     Bcircular2.set_points(points)
     dB1_by_dX = Bfield.dB_by_dX()
     transpGradB1 = [dBdx.T for dBdx in dB1_by_dX]
     assert np.allclose(Bfield.B(), Bcircular.B())
     assert np.allclose(Bfield.B(), Bcircular2.B())
     assert np.allclose(Bfield.dB_by_dX(), Bcircular.dB_by_dX())
     assert np.allclose(Bfield.dB_by_dX(), Bcircular2.dB_by_dX())
     assert np.allclose(dB1_by_dX[:, 0, 0] +
                        dB1_by_dX[:, 1, 1] + dB1_by_dX[:, 2, 2],
                        np.zeros((npoints)))  # divergence
     assert np.allclose(dB1_by_dX, transpGradB1)  # symmetry of the gradient