Beispiel #1
0
    def eval_direct(self, target_boxes, neighbor_sources_starts,
            neighbor_sources_lists, src_weights):
        pot = self.potential_zeros()

        from pyfmmlib import hpotgrad2dall_vec

        for itgt_box, tgt_ibox in enumerate(target_boxes):
            tgt_pslice = self._get_target_slice(tgt_ibox)

            if tgt_pslice.stop - tgt_pslice.start == 0:
                continue

            tgt_result = np.zeros(tgt_pslice.stop - tgt_pslice.start, np.complex128)
            start, end = neighbor_sources_starts[itgt_box:itgt_box+2]
            for src_ibox in neighbor_sources_lists[start:end]:
                src_pslice = self._get_source_slice(src_ibox)

                if src_pslice.stop - src_pslice.start == 0:
                    continue

                tmp_pot, _, _ = hpotgrad2dall_vec(
                        ifgrad=False, ifhess=False,
                        sources=self._get_sources(src_pslice),
                        charge=src_weights[src_pslice],
                        targets=self._get_targets(tgt_pslice), zk=self.helmholtz_k)

                tgt_result += tmp_pot

            pot[tgt_pslice] = tgt_result

        return pot
    def eval_direct(self, target_boxes, neighbor_sources_starts,
                    neighbor_sources_lists, src_weights):
        pot = self.potential_zeros()

        from pyfmmlib import hpotgrad2dall_vec

        for itgt_box, tgt_ibox in enumerate(target_boxes):
            tgt_pslice = self._get_target_slice(tgt_ibox)

            if tgt_pslice.stop - tgt_pslice.start == 0:
                continue

            tgt_result = np.zeros(tgt_pslice.stop - tgt_pslice.start,
                                  np.complex128)
            start, end = neighbor_sources_starts[itgt_box:itgt_box + 2]
            for src_ibox in neighbor_sources_lists[start:end]:
                src_pslice = self._get_source_slice(src_ibox)

                if src_pslice.stop - src_pslice.start == 0:
                    continue

                tmp_pot, _, _ = hpotgrad2dall_vec(
                    ifgrad=False,
                    ifhess=False,
                    sources=self._get_sources(src_pslice),
                    charge=src_weights[src_pslice],
                    targets=self._get_targets(tgt_pslice),
                    zk=self.helmholtz_k)

                tgt_result += tmp_pot

            pot[tgt_pslice] = tgt_result

        return pot
Beispiel #3
0
def test_pyfmmlib_fmm(ctx_getter):
    logging.basicConfig(level=logging.INFO)

    from pytest import importorskip
    importorskip("pyfmmlib")

    ctx = ctx_getter()
    queue = cl.CommandQueue(ctx)

    nsources = 3000
    ntargets = 1000
    dims = 2
    dtype = np.float64

    helmholtz_k = 2

    sources = p_normal(queue, nsources, dims, dtype, seed=15)
    targets = (
            p_normal(queue, ntargets, dims, dtype, seed=18)
            + np.array([2, 0]))

    sources_host = particle_array_to_host(sources)
    targets_host = particle_array_to_host(targets)

    from boxtree import TreeBuilder
    tb = TreeBuilder(ctx)

    tree, _ = tb(queue, sources, targets=targets,
            max_particles_in_box=30, debug=True)

    from boxtree.traversal import FMMTraversalBuilder
    tbuild = FMMTraversalBuilder(ctx)
    trav, _ = tbuild(queue, tree, debug=True)

    trav = trav.get(queue=queue)

    from pyopencl.clrandom import PhiloxGenerator
    rng = PhiloxGenerator(queue.context, seed=20)

    weights = rng.uniform(queue, nsources, dtype=np.float64).get()
    #weights = np.ones(nsources)

    logger.info("computing direct (reference) result")

    from pyfmmlib import hpotgrad2dall_vec
    ref_pot, _, _ = hpotgrad2dall_vec(ifgrad=False, ifhess=False,
            sources=sources_host.T, charge=weights,
            targets=targets_host.T, zk=helmholtz_k)

    from boxtree.pyfmmlib_integration import Helmholtz2DExpansionWrangler
    wrangler = Helmholtz2DExpansionWrangler(trav.tree, helmholtz_k, nterms=10)

    from boxtree.fmm import drive_fmm
    pot = drive_fmm(trav, wrangler, weights)

    rel_err = la.norm(pot - ref_pot) / la.norm(ref_pot)
    logger.info("relative l2 error: %g" % rel_err)
    assert rel_err < 1e-5
Beispiel #4
0
def test_translations():
    nterms = 15
    zk = 3
    rscale = 1

    n = 40
    # centered at the origin, extent [-.5,.5]
    sources = np.random.uniform(size=(n, 2)) - 0.5
    charges = np.random.uniform(size=n)

    targets_center = np.array([10, 0])
    targets = np.random.uniform(size=(n, 2)) - 0.5 + targets_center

    from pyfmmlib import (h2dformmp, h2dmpmp_vec, h2dmploc_vec, h2dlocloc_vec,
                          h2dtaeval_vec, hpotgrad2dall_vec, h2dmpeval_vec)

    ref_value, _, _ = hpotgrad2dall_vec(ifgrad=False,
                                        ifhess=False,
                                        sources=sources.T,
                                        charge=charges,
                                        targets=targets.T,
                                        zk=zk)

    # {{{ multipole 1

    mp1_center = np.array([0, 0])
    ier, mp1 = h2dformmp(zk, rscale, sources.T, charges, mp1_center, nterms)
    assert ier == 0

    mp1_value, _, _ = h2dmpeval_vec(zk,
                                    rscale,
                                    mp1_center,
                                    mp1,
                                    ztarg=targets.T,
                                    ifgrad=False,
                                    ifhess=False)

    assert la.norm(mp1_value - ref_value) / la.norm(ref_value) < 1e-12

    # }}}

    # {{{ multipole 2

    mp2_center = np.array([2, 0])
    mp2 = h2dmpmp_vec(zk, rscale, mp1_center, mp1, rscale, mp2_center, nterms)

    mp2_value, _, _ = h2dmpeval_vec(zk,
                                    rscale,
                                    mp2_center,
                                    mp2,
                                    ztarg=targets.T,
                                    ifgrad=False,
                                    ifhess=False)

    assert la.norm(mp2_value - ref_value) / la.norm(ref_value) < 3e-5

    # }}}

    # {{{ local 1

    loc1_center = targets_center - np.array([1, 0])
    loc1 = h2dmploc_vec(zk, rscale, mp2_center, mp2, rscale, loc1_center,
                        nterms)

    loc1_value, _, _ = h2dtaeval_vec(zk,
                                     rscale,
                                     loc1_center,
                                     loc1,
                                     ztarg=targets.T,
                                     ifgrad=False,
                                     ifhess=False)

    assert la.norm(loc1_value - ref_value) / la.norm(ref_value) < 3e-5

    # }}}

    # {{{ local 2

    loc2_center = targets_center
    loc2 = h2dlocloc_vec(zk, rscale, loc1_center, loc1, rscale, loc2_center,
                         nterms)

    loc2_value, _, _ = h2dtaeval_vec(zk,
                                     rscale,
                                     loc2_center,
                                     loc2,
                                     ztarg=targets.T,
                                     ifgrad=False,
                                     ifhess=False)

    assert la.norm(loc2_value - ref_value) / la.norm(ref_value) < 1e-4
Beispiel #5
0
def test_translations():
    nterms = 15
    zk = 3
    rscale = 1

    n = 40
    # centered at the origin, extent [-.5,.5]
    sources = np.random.uniform(size=(n, 2)) - 0.5
    charges = np.random.uniform(size=n)

    targets_center = np.array([10, 0])
    targets = np.random.uniform(size=(n, 2)) - 0.5 + targets_center

    from pyfmmlib import (h2dformmp, h2dmpmp_vec, h2dmploc_vec,
            h2dlocloc_vec, h2dtaeval_vec, hpotgrad2dall_vec, h2dmpeval_vec)

    ref_value, _, _ = hpotgrad2dall_vec(ifgrad=False, ifhess=False,
            sources=sources.T, charge=charges,
            targets=targets.T, zk=zk)

    # {{{ multipole 1

    mp1_center = np.array([0, 0])
    ier, mp1 = h2dformmp(zk, rscale, sources.T, charges, mp1_center, nterms)
    assert ier == 0

    mp1_value, _, _ = h2dmpeval_vec(zk, rscale, mp1_center, mp1, ztarg=targets.T,
            ifgrad=False, ifhess=False)

    assert la.norm(mp1_value - ref_value) / la.norm(ref_value) < 1e-12

    # }}}

    # {{{ multipole 2

    mp2_center = np.array([2, 0])
    mp2 = h2dmpmp_vec(zk, rscale, mp1_center, mp1, rscale, mp2_center, nterms)

    mp2_value, _, _ = h2dmpeval_vec(zk, rscale, mp2_center, mp2, ztarg=targets.T,
            ifgrad=False, ifhess=False)

    assert la.norm(mp2_value - ref_value) / la.norm(ref_value) < 3e-5

    # }}}

    # {{{ local 1

    loc1_center = targets_center - np.array([1, 0])
    loc1 = h2dmploc_vec(zk, rscale, mp2_center, mp2, rscale, loc1_center, nterms)

    loc1_value, _, _ = h2dtaeval_vec(zk, rscale, loc1_center, loc1,
            ztarg=targets.T, ifgrad=False, ifhess=False)

    assert la.norm(loc1_value - ref_value) / la.norm(ref_value) < 3e-5

    # }}}

    # {{{ local 2

    loc2_center = targets_center
    loc2 = h2dlocloc_vec(zk, rscale, loc1_center, loc1, rscale, loc2_center, nterms)

    loc2_value, _, _ = h2dtaeval_vec(zk, rscale, loc2_center, loc2, ztarg=targets.T,
            ifgrad=False, ifhess=False)

    assert la.norm(loc2_value - ref_value) / la.norm(ref_value) < 1e-4
Beispiel #6
0
def test_pyfmmlib_fmm(ctx_getter):
    logging.basicConfig(level=logging.INFO)

    from pytest import importorskip
    importorskip("pyfmmlib")

    ctx = ctx_getter()
    queue = cl.CommandQueue(ctx)

    nsources = 3000
    ntargets = 1000
    dims = 2
    dtype = np.float64

    helmholtz_k = 2

    sources = p_normal(queue, nsources, dims, dtype, seed=15)
    targets = (p_normal(queue, ntargets, dims, dtype, seed=18) +
               np.array([2, 0]))

    sources_host = particle_array_to_host(sources)
    targets_host = particle_array_to_host(targets)

    from boxtree import TreeBuilder
    tb = TreeBuilder(ctx)

    tree, _ = tb(queue,
                 sources,
                 targets=targets,
                 max_particles_in_box=30,
                 debug=True)

    from boxtree.traversal import FMMTraversalBuilder
    tbuild = FMMTraversalBuilder(ctx)
    trav, _ = tbuild(queue, tree, debug=True)

    trav = trav.get(queue=queue)

    from pyopencl.clrandom import RanluxGenerator
    rng = RanluxGenerator(queue, seed=20)

    weights = rng.uniform(queue, nsources, dtype=np.float64).get()
    #weights = np.ones(nsources)

    logger.info("computing direct (reference) result")

    from pyfmmlib import hpotgrad2dall_vec
    ref_pot, _, _ = hpotgrad2dall_vec(ifgrad=False,
                                      ifhess=False,
                                      sources=sources_host.T,
                                      charge=weights,
                                      targets=targets_host.T,
                                      zk=helmholtz_k)

    from boxtree.pyfmmlib_integration import Helmholtz2DExpansionWrangler
    wrangler = Helmholtz2DExpansionWrangler(trav.tree, helmholtz_k, nterms=10)

    from boxtree.fmm import drive_fmm
    pot = drive_fmm(trav, wrangler, weights)

    rel_err = la.norm(pot - ref_pot) / la.norm(ref_pot)
    logger.info("relative l2 error: %g" % rel_err)
    assert rel_err < 1e-5