示例#1
0
    def test_residual(self):
        """
        This test loads a SurfaceXYZFourier that interpolates the xyz coordinates
        of a surface in the NCSX configuration that was computed on a previous
        branch of pyplasmaopt.  Here, we verify that the  Boozer residual at these 
        interpolation points is small.
        """

        s = get_exact_surface()
        coils, currents, ma = get_ncsx_data()
        stellarator = CoilCollection(coils, currents, 3, True)
        bs = BiotSavart(stellarator.coils, stellarator.currents)
        bs_tf = BiotSavart(stellarator.coils, stellarator.currents)

        weight = 1.
        tf = ToroidalFlux(s, bs_tf)

        # these data are obtained from `boozer` branch of pyplamsaopt
        tf_target = 0.41431152
        iota = -0.44856192

        boozer_surface = BoozerSurface(bs, s, tf, tf_target)
        x = np.concatenate((s.get_dofs(), [iota]))
        r0 = boozer_surface.boozer_penalty_constraints(
            x,
            derivatives=0,
            constraint_weight=weight,
            optimize_G=False,
            scalarize=False)
        # the residual should be close to zero for all entries apart from the y
        # and z coordinate at phi=0 and theta=0 (and the corresponding rotations)
        ignores_idxs = np.zeros_like(r0)
        ignores_idxs[[1, 2, 693, 694, 695, 1386, 1387, 1388, -2, -1]] = 1
        assert np.max(np.abs(r0[ignores_idxs < 0.5])) < 1e-8
        assert np.max(np.abs(r0[-2:])) < 1e-6
示例#2
0
 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)
示例#3
0
    def subtest_boozer_penalty_constraints_gradient(self,
                                                    surfacetype,
                                                    stellsym,
                                                    optimize_G=False):
        np.random.seed(1)
        coils, currents, ma = get_ncsx_data()
        stellarator = CoilCollection(coils, currents, 3, True)

        bs = BiotSavart(stellarator.coils, stellarator.currents)
        bs_tf = BiotSavart(stellarator.coils, stellarator.currents)

        s = get_surface(surfacetype, stellsym)
        s.fit_to_curve(ma, 0.1)

        weight = 11.1232

        tf = ToroidalFlux(s, bs_tf)

        tf_target = 0.1
        boozer_surface = BoozerSurface(bs, s, tf, tf_target)

        iota = -0.3
        x = np.concatenate((s.get_dofs(), [iota]))
        if optimize_G:
            x = np.concatenate((x, [
                2. * np.pi * np.sum(np.abs(bs.coil_currents)) *
                (4 * np.pi * 10**(-7) / (2 * np.pi))
            ]))
        f0, J0 = boozer_surface.boozer_penalty_constraints(
            x, derivatives=1, constraint_weight=weight, optimize_G=optimize_G)

        h = np.random.uniform(size=x.shape) - 0.5
        Jex = J0 @ h

        err_old = 1e9
        epsilons = np.power(2., -np.asarray(range(7, 20)))
        print(
            "################################################################################"
        )
        for eps in epsilons:
            f1 = boozer_surface.boozer_penalty_constraints(
                x + eps * h,
                derivatives=0,
                constraint_weight=weight,
                optimize_G=optimize_G)
            Jfd = (f1 - f0) / eps
            err = np.linalg.norm(Jfd - Jex) / np.linalg.norm(Jex)
            print(err / err_old, f0, f1)
            assert err < err_old * 0.55
            err_old = err
        print(
            "################################################################################"
        )
示例#4
0
    def subtest_boozer_constrained_jacobian(self,
                                            surfacetype,
                                            stellsym,
                                            optimize_G=False):
        np.random.seed(1)
        coils, currents, ma = get_ncsx_data()
        stellarator = CoilCollection(coils, currents, 3, True)

        bs = BiotSavart(stellarator.coils, stellarator.currents)
        bs_tf = BiotSavart(stellarator.coils, stellarator.currents)

        s = get_surface(surfacetype, stellsym)
        s.fit_to_curve(ma, 0.1)

        tf = ToroidalFlux(s, bs_tf)

        tf_target = 0.1
        boozer_surface = BoozerSurface(bs, s, tf, tf_target)

        iota = -0.3
        lm = [0., 0.]
        x = np.concatenate((s.get_dofs(), [iota]))
        if optimize_G:
            x = np.concatenate((x, [
                2. * np.pi * np.sum(np.abs(bs.coil_currents)) *
                (4 * np.pi * 10**(-7) / (2 * np.pi))
            ]))
        xl = np.concatenate((x, lm))
        res0, dres0 = boozer_surface.boozer_exact_constraints(
            xl, derivatives=1, optimize_G=optimize_G)

        h = np.random.uniform(size=xl.shape) - 0.5
        dres_exact = dres0 @ h

        err_old = 1e9
        epsilons = np.power(2., -np.asarray(range(7, 20)))
        print(
            "################################################################################"
        )
        for eps in epsilons:
            res1 = boozer_surface.boozer_exact_constraints(
                xl + eps * h, derivatives=0, optimize_G=optimize_G)
            dres_fd = (res1 - res0) / eps
            err = np.linalg.norm(dres_fd - dres_exact)
            print(err / err_old)
            assert err < err_old * 0.55
            err_old = err
        print(
            "################################################################################"
        )
示例#5
0
    def test_interpolated_field_convergence_rate(self):
        R0test = 1.5
        B0test = 0.8
        B0 = ToroidalField(R0test, B0test)

        coils, currents, _ = get_ncsx_data(Nt_coils=5, Nt_ma=10, ppp=5)
        stellarator = CoilCollection(coils, currents, 3, True)
        bs = BiotSavart(stellarator.coils, stellarator.currents)
        old_err_1 = 1e6
        old_err_2 = 1e6
        btotal = bs + B0

        for n in [4, 8, 16]:
            rmin = 1.5
            rmax = 1.7
            rsteps = n
            phimin = 0
            phimax = 2 * np.pi
            phisteps = n * 16
            zmin = -0.1
            zmax = 0.1
            zsteps = n
            bsh = InterpolatedField(btotal, 2, [rmin, rmax, rsteps],
                                    [phimin, phimax, phisteps],
                                    [zmin, zmax, zsteps], True)
            err_1 = np.mean(bsh.estimate_error_B(1000))
            err_2 = np.mean(bsh.estimate_error_GradAbsB(1000))
            print(err_1, err_2)
            assert err_1 < 0.6**3 * old_err_1
            assert err_2 < 0.6**3 * old_err_2
            old_err_1 = err_1
            old_err_2 = err_2
示例#6
0
 def test_poincare_plot(self):
     coils, currents, ma = get_ncsx_data(Nt_coils=15)
     nfp = 3
     stellarator = CoilCollection(coils, currents, nfp, True)
     bs = BiotSavart(stellarator.coils, stellarator.currents)
     n = 10
     rrange = (1.0, 1.9, n)
     phirange = (0, 2*np.pi/nfp, n*2)
     zrange = (0, 0.4, n)
     bsh = InterpolatedField(
         bs, UniformInterpolationRule(2),
         rrange, phirange, zrange, True, nfp=3, stellsym=True
     )
     nlines = 4
     r0 = np.linalg.norm(ma.gamma()[0, :2])
     z0 = ma.gamma()[0, 2]
     R0 = [r0 + i*0.01 for i in range(nlines)]
     Z0 = [z0 for i in range(nlines)]
     nphis = 4
     phis = np.linspace(0, 2*np.pi/nfp, nphis, endpoint=False)
     res_tys, res_phi_hits = compute_fieldlines(
         bsh, R0, Z0, tmax=1000, phis=phis, stopping_criteria=[])
     try:
         import matplotlib  # noqa
         plot_poincare_data(res_phi_hits, phis, '/tmp/fieldlines.png')
     except ImportError:
         pass
示例#7
0
    def subtest_boozer_penalty_constraints_hessian(self,
                                                   surfacetype,
                                                   stellsym,
                                                   optimize_G=False):
        np.random.seed(1)
        coils, currents, ma = get_ncsx_data()
        stellarator = CoilCollection(coils, currents, 3, True)

        bs = BiotSavart(stellarator.coils, stellarator.currents)
        bs_tf = BiotSavart(stellarator.coils, stellarator.currents)

        s = get_surface(surfacetype, stellsym)
        s.fit_to_curve(ma, 0.1)

        tf = ToroidalFlux(s, bs_tf)

        tf_target = 0.1
        boozer_surface = BoozerSurface(bs, s, tf, tf_target)

        iota = -0.3
        x = np.concatenate((s.get_dofs(), [iota]))
        if optimize_G:
            x = np.concatenate((x, [
                2. * np.pi * np.sum(np.abs(bs.coil_currents)) *
                (4 * np.pi * 10**(-7) / (2 * np.pi))
            ]))
        f0, J0, H0 = boozer_surface.boozer_penalty_constraints(
            x, derivatives=2, optimize_G=optimize_G)

        h1 = np.random.uniform(size=x.shape) - 0.5
        h2 = np.random.uniform(size=x.shape) - 0.5
        d2f = h1 @ H0 @ h2

        err_old = 1e9
        epsilons = np.power(2., -np.asarray(range(10, 20)))
        print(
            "################################################################################"
        )
        for eps in epsilons:
            fp, Jp = boozer_surface.boozer_penalty_constraints(
                x + eps * h1, derivatives=1, optimize_G=optimize_G)
            d2f_fd = (Jp @ h2 - J0 @ h2) / eps
            err = np.abs(d2f_fd - d2f) / np.abs(d2f)
            print(err / err_old)
            assert err < err_old * 0.55
            err_old = err
示例#8
0
    def test_get_set_points_cyl_cart(self):
        coils, currents, _ = get_ncsx_data(Nt_coils=5, Nt_ma=10, ppp=5)
        stellarator = CoilCollection(coils, currents, 3, True)
        bs = BiotSavart(stellarator.coils, stellarator.currents)

        points_xyz = np.asarray([[0.5, 0.6, 0.7]])
        points_rphiz = np.zeros_like(points_xyz)
        points_rphiz[:, 0] = np.linalg.norm(points_xyz[:, 0:2], axis=1)
        points_rphiz[:, 1] = np.mod(
            np.arctan2(points_xyz[:, 1], points_xyz[:, 0]), 2 * np.pi)
        points_rphiz[:, 2] = points_xyz[:, 2]
        bs.set_points_cyl(points_rphiz)
        # import IPython; IPython.embed()
        # import sys; sys.exit()
        assert np.allclose(bs.get_points_cyl(), points_rphiz)
        assert np.allclose(bs.get_points_cart(), points_xyz)

        bs.set_points_cart(points_xyz)
        assert np.allclose(bs.get_points_cyl(), points_rphiz)
        assert np.allclose(bs.get_points_cart(), points_xyz)
示例#9
0
 def test_poincare_ncsx_known(self):
     coils, currents, ma = get_ncsx_data(Nt_coils=25)
     nfp = 3
     stellarator = CoilCollection(coils, currents, nfp, True)
     currents = [-c for c in currents]
     bs = BiotSavart(stellarator.coils, stellarator.currents)
     R0 = [np.linalg.norm(ma.gamma()[0, :2])]
     Z0 = [ma.gamma()[0, 2]]
     phis = np.arctan2(ma.gamma()[:, 1], ma.gamma()[:, 0])
     res_tys, res_phi_hits = compute_fieldlines(
         bs, R0, Z0, tmax=10, phis=phis, stopping_criteria=[])
     for i in range(len(phis)-1):
         assert np.linalg.norm(ma.gamma()[i+1, :] - res_phi_hits[0][i, 2:5]) < 1e-4
示例#10
0
 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
示例#11
0
    def test_interpolated_field_close_with_symmetries(self):
        R0test = 1.5
        B0test = 0.8
        B0 = ToroidalField(R0test, B0test)

        coils, currents, _ = get_ncsx_data(Nt_coils=10, Nt_ma=10, ppp=5)
        nfp = 3
        stellarator = CoilCollection(coils, currents, nfp, True)
        bs = BiotSavart(stellarator.coils, stellarator.currents)
        btotal = bs + B0
        n = 12
        rmin = 1.5
        rmax = 1.7
        rsteps = n
        phimin = 0
        phimax = 2 * np.pi / nfp
        phisteps = n * 32 // nfp
        zmin = 0.
        zmax = 0.1
        zsteps = n // 2
        bsh = InterpolatedField(btotal,
                                4, [rmin, rmax, rsteps],
                                [phimin, phimax, phisteps],
                                [zmin, zmax, zsteps],
                                True,
                                nfp=nfp,
                                stellsym=True)
        N = 1000
        points = np.random.uniform(size=(N, 3))
        points[:, 0] = points[:, 0] * (rmax - rmin) + rmin
        points[:, 1] = points[:, 1] * (nfp * phimax - phimin) + phimin
        points[:, 2] = points[:, 2] * (2 * zmax) - zmax
        btotal.set_points_cyl(points)
        dB = btotal.GradAbsB()
        B = btotal.B()
        dBc = btotal.GradAbsB_cyl()
        Bc = btotal.B_cyl()
        bsh.set_points_cyl(points)
        Bh = bsh.B()
        dBh = bsh.GradAbsB()
        Bhc = bsh.B_cyl()
        dBhc = bsh.GradAbsB_cyl()
        assert np.allclose(B, Bh, rtol=1e-3)
        assert np.allclose(dB, dBh, rtol=1e-3)
        assert np.allclose(Bc, Bhc, rtol=1e-3)
        assert np.allclose(dBc, dBhc, rtol=1e-3)
示例#12
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)
示例#13
0
    def test_interpolated_field_close_no_sym(self):
        R0test = 1.5
        B0test = 0.8
        B0 = ToroidalField(R0test, B0test)

        coils, currents, _ = get_ncsx_data(Nt_coils=5, Nt_ma=10, ppp=5)
        stellarator = CoilCollection(coils, currents, 3, True)
        bs = BiotSavart(stellarator.coils, stellarator.currents)
        btotal = bs + B0
        n = 8
        rmin = 1.5
        rmax = 1.7
        rsteps = n
        phimin = 0
        phimax = 2 * np.pi
        phisteps = n * 16
        zmin = -0.1
        zmax = 0.1
        zsteps = n
        bsh = InterpolatedField(btotal, 4, [rmin, rmax, rsteps],
                                [phimin, phimax, phisteps],
                                [zmin, zmax, zsteps], True)
        N = 100
        points = np.random.uniform(size=(N, 3))
        points[:, 0] = points[:, 0] * (rmax - rmin) + rmin
        points[:, 1] = points[:, 1] * (phimax - phimin) + phimin
        points[:, 2] = points[:, 2] * (zmax - zmin) + zmin
        btotal.set_points_cyl(points)
        dB = btotal.GradAbsB()
        B = btotal.B()
        dBc = btotal.GradAbsB_cyl()
        Bc = btotal.B_cyl()
        bsh.set_points_cyl(points)
        Bh = bsh.B()
        dBh = bsh.GradAbsB()
        Bhc = bsh.B_cyl()
        dBhc = bsh.GradAbsB_cyl()
        assert np.allclose(B, Bh, rtol=1e-2)
        assert np.allclose(dB, dBh, rtol=1e-2)
        assert np.allclose(Bc, Bhc, rtol=1e-2)
        assert np.allclose(dBc, dBhc, rtol=1e-2)
示例#14
0
    def test_poincare_caryhanson(self):
        # Test with a known magnetic field - optimized Cary&Hanson configuration
        # with a magnetic axis at R=0.9413. Field created using the Biot-Savart
        # solver given a set of two helical coils created using the CurveHelical
        # class. The total magnetic field is a superposition of a helical and
        # a toroidal magnetic field.
        coils = [CurveHelical(200, 2, 5, 2, 1., 0.3) for i in range(2)]
        coils[0].set_dofs(np.concatenate(([np.pi/2, 0.2841], [0, 0])))
        coils[1].set_dofs(np.concatenate(([0, 0], [0, 0.2933])))
        currents = [3.07e5, -3.07e5]
        Btoroidal = ToroidalField(1.0, 1.0)
        Bhelical = BiotSavart(coils, currents)
        bs = Bhelical+Btoroidal
        ma = CurveXYZFourier(300, 1)
        magnetic_axis_radius = 0.9413
        ma.set_dofs([0, 0, magnetic_axis_radius, 0, magnetic_axis_radius, 0, 0, 0, 0])
        R0 = [np.linalg.norm(ma.gamma()[0, :2])]
        Z0 = [ma.gamma()[0, 2]]        
        phis = np.arctan2(ma.gamma()[:, 1], ma.gamma()[:, 0])
        res_tys, res_phi_hits = compute_fieldlines(
            bs, R0, Z0, tmax=2, phis=phis, stopping_criteria=[])

        for i in range(len(res_phi_hits[0])):
            assert np.linalg.norm(ma.gamma()[i+1, :] - res_phi_hits[0][i, 2:5]) < 2e-3
示例#15
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())