コード例 #1
0
    def _filter(data, size=10, cval = 0, res_g=None, sub_blocks=(1, 1, 1)):
        if np.isscalar(size):
            size = (size,)*len(data.shape)

        if isinstance(data, np.ndarray):
            if sub_blocks is None or set(sub_blocks) == {1}:
                return _filter_numpy(data, size, cval)
            else:
                # cut the image into tile and operate on every of them
                N_sub = [int(np.ceil(1. * n / s)) for n, s in zip(data.shape, sub_blocks)]
                Npads = int(size // 2)
                res = np.empty(data.shape, np.float32)
                for i, (data_tile, data_s_src, data_s_dest) \
                        in enumerate(tile_iterator(data, blocksize=N_sub,
                                                   padsize=Npads,
                                                   mode="constant")):
                    res_tile = _filter_numpy(data_tile.copy(),
                                                 size, cval)
                    res[data_s_src] = res_tile[data_s_dest]
                return res

        elif isinstance(data, OCLArray):
            return filter_gpu(data, size=size, cval = cval, res_g=res_g)
        else:
            raise TypeError("array argument (1) has bad type: %s" % type(data))
コード例 #2
0
def convolve_spatial2(im, psfs,
                      mode = "constant",
                      grid_dim = None,
                      sub_blocks = None,
                      pad_factor = 2,
                      plan = None,
                      return_plan = False):
    """
    GPU accelerated spatial varying convolution of an 2d image with a
    (Gy,Gx) grid of psfs assumed to be equally spaced within the image
    the input image im is subdivided into (Gy,Gx) blocks, each block is
    convolved with the corresponding psf and linearly interpolated to give the
    final rresult

    The psfs can be given either in

    A) Stackmode
    psfs.shape =  (Gy,Gx, Hy, Hx)
    then psfs[j,i] is the psf at the center of each block (i,j) in the image

    B) Flatmode
    psfs.shape = im.shape
    then the psfs are assumed to be definied on the gridpoints of the images itself
    in this case grid_dim = (Gy,Gx) has to be given

    as of now each image dimension has to be divisible by the grid dim, i.e.
    ::
        Nx % Gx == 0
        Ny % Gy == 0

    GPU Memory consumption is of order 8*Nx*Ny
    If not enough GPU memory is available, consider using
    sub_blocks = (n,m)
    then the operation is carried out in a tiled fashion reducing
    memory consumption to 8*Nx*Ny*(1/n+2/Gx)*(1/m+2/Gy)

    Example
    -------


    im = np.zeros((128,128))
    im[::10,::10] = 1.

    # Stackmode
    psfs = np.ones((16,16,4,4))
    res = convolve_spatial2(im, psfs, mode = "wrap")

    # Flatmode
    _X,_Y = np.meshgrid(*(np.arange(128),)*2)
    psfs = np.clip(np.sin(2*np.pi*_X/8),0,1)*np.clip(np.cos(2*np.pi*_Y/8),0,1)
    res = convolve_spatial2(im, psfs, grid_dim = (16,16))


    Parameters
    ----------
    im: ndarray
        the image to convolve
    psfs: ndarray
        the (Gx,Gy) psf grid, either of shape (Gx,Gy, Hy, Hx) or im.shape

    mode: string, optional
        padding mode, either "constant" or "wrap"
    grid_dim: tuple, optional
        the (Gy,Gx) grid dimension, has to be provided if psfs.shape = im.shape

    sub_blocks: tuple, optional
        tiling mode, give e.g. (2,2) to sequentially operate on quadratnts
    pad_factor: int
        the factor of its size each block get tiled, use pad_factor=2 if the psfs
        are well localized, use pad_factor = 3 if not (e.g. if you experience blocking)_

    plan: fft_plan, optional
        when given use this as the fft plan
    return_plan: bool, optional
        return (res, plan) with plan being the fft plan for further use

    Returns
    -------
    res: ndarray
        the convolved image



    """

    ndim = im.ndim

    if ndim != 2:
        raise ValueError("wrong dimensions of input!")


    if grid_dim:
        if psfs.shape != im.shape:
            raise ValueError("if grid_dim is set, then im.shape = hs.shape !")
    else:
        if not psfs.ndim==2*ndim:
            raise ValueError("wrong dimensions of psf grid! (Gy,Gx,Ny,Nx)")

    if grid_dim:
        Gs = grid_dim
    else:
        Gs = psfs.shape[:ndim]

    if not np.all([n%g==0 for n,g in zip(im.shape,Gs)]):
        raise NotImplementedError("shape of image has to be divisible by Gx Gy  = %s shape mismatch"%(str(psfs.shape[:2])))

    if sub_blocks is None:
        return _convolve_spatial2(im,
                                  psfs,
                                  mode = mode,
                                  pad_factor = pad_factor,
                                  plan = plan,
                                  return_plan = return_plan,
                                  grid_dim = grid_dim)
    else:
        # cut the image into tile and operate on every of them
        N_sub = [n/s for n,s  in zip(im.shape,sub_blocks)]
        Nblocks = [n/g for n,g  in zip(im.shape,Gs)]
        Npads = [n*(s>1) for n,s  in zip(Nblocks, sub_blocks)]
        grid_dim_sub = [g/s+2*(s>1) for g,s   in zip(Gs, sub_blocks)]

        print N_sub, Nblocks, grid_dim_sub, Npads

        if grid_dim:
            res = np.empty(im.shape, np.float32)
            plan = None
            for (im_tile, im_s_src, im_s_dest), (hs_tile, hs_s_src, hs_s_dest)\
                in zip(tile_iterator(im,blocksize=N_sub,
                                     padsize=Npads,
                                     mode = mode),\
                    tile_iterator(psfs, blocksize=N_sub,
                                  padsize=Npads,
                                  mode = mode)):

                res_tile, plan = _convolve_spatial2(im_tile.copy(),
                                              hs_tile.copy(),
                                              mode = mode,
                                              pad_factor = pad_factor,
                                              return_plan=True,
                                              plan = plan,
                                              grid_dim = grid_dim_sub)


                res[im_s_src] = res_tile[im_s_dest]
            return res

        else:
            raise NotImplementedError()
コード例 #3
0
def convolve_spatial2(im,
                      psfs,
                      mode="constant",
                      grid_dim=None,
                      sub_blocks=None,
                      pad_factor=2,
                      plan=None,
                      return_plan=False):
    """
    GPU accelerated spatial varying convolution of an 2d image with a
    (Gy,Gx) grid of psfs assumed to be equally spaced within the image
    the input image im is subdivided into (Gy,Gx) blocks, each block is
    convolved with the corresponding psf and linearly interpolated to give the
    final result

    The psfs can be given either in

    A) Stackmode
    psfs.shape =  (Gy,Gx, Hy, Hx)
    then psfs[j,i] is the psf at the center of each block (i,j) in the image

    B) Flatmode
    psfs.shape = im.shape
    then the psfs are assumed to be definied on the gridpoints of the images itself
    in this case grid_dim = (Gy,Gx) has to be given

    as of now each image dimension has to be divisible by the grid dim, i.e.
    ::
        Nx % Gx == 0
        Ny % Gy == 0

    GPU Memory consumption is of order 8*Nx*Ny
    If not enough GPU memory is available, consider using
    sub_blocks = (n,m)
    then the operation is carried out in a tiled fashion reducing
    memory consumption to 8*Nx*Ny*(1/n+2/Gx)*(1/m+2/Gy)

    Example
    -------


    im = np.zeros((128,128))
    im[::10,::10] = 1.

    # Stackmode
    psfs = np.ones((16,16,4,4))
    res = convolve_spatial2(im, psfs, mode = "wrap")

    # Flatmode
    _X,_Y = np.meshgrid(*(np.arange(128),)*2)
    psfs = np.clip(np.sin(2*np.pi*_X/8),0,1)*np.clip(np.cos(2*np.pi*_Y/8),0,1)
    res = convolve_spatial2(im, psfs, grid_dim = (16,16))


    Parameters
    ----------
    im: ndarray
        the image to convolve
    psfs: ndarray
        the (Gx,Gy) psf grid, either of shape (Gx,Gy, Hy, Hx) or im.shape

    mode: string, optional
        padding mode, either "constant" or "wrap"
    grid_dim: tuple, optional
        the (Gy,Gx) grid dimension, has to be provided if psfs.shape = im.shape

    sub_blocks: tuple, optional
        tiling mode, give e.g. (2,2) to sequentially operate on quadratnts
    pad_factor: int
        the factor of its size each block get tiled, use pad_factor=2 if the psfs
        are well localized, use pad_factor = 3 if not (e.g. if you experience blocking)_

    plan: fft_plan, optional
        when given use this as the fft plan
    return_plan: bool, optional
        return (res, plan) with plan being the fft plan for further use

    Returns
    -------
    res: ndarray
        the convolved image



    """

    ndim = im.ndim

    if ndim != 2:
        raise ValueError("wrong dimensions of input!")

    if grid_dim:
        if psfs.shape != im.shape:
            raise ValueError("if grid_dim is set, then im.shape = hs.shape !")
    else:
        if not psfs.ndim == 2 * ndim:
            raise ValueError("wrong dimensions of psf grid! (Gy,Gx,Ny,Nx)")

    if grid_dim:
        Gs = grid_dim
    else:
        Gs = psfs.shape[:ndim]

    if not np.all([n % g == 0 for n, g in zip(im.shape, Gs)]):
        raise NotImplementedError(
            "shape of image has to be divisible by Gx Gy  = %s shape mismatch"
            % (str(psfs.shape[:2])))

    if sub_blocks is None:
        return _convolve_spatial2(im,
                                  psfs,
                                  mode=mode,
                                  pad_factor=pad_factor,
                                  plan=plan,
                                  return_plan=return_plan,
                                  grid_dim=grid_dim)
    else:
        # cut the image into tile and operate on every of them
        N_sub = [n // s for n, s in zip(im.shape, sub_blocks)]
        Nblocks = [n // g for n, g in zip(im.shape, Gs)]
        Npads = [n * (s > 1) for n, s in zip(Nblocks, sub_blocks)]
        grid_dim_sub = [g // s + 2 * (s > 1) for g, s in zip(Gs, sub_blocks)]

        logger.debug(
            "N_sub: {}, Nblocks: {}, grid_dim_sub, {}, Npads, {}".format(
                N_sub, Nblocks, grid_dim_sub, Npads))

        if grid_dim:
            res = np.empty(im.shape, np.float32)
            plan = None
            for (im_tile, im_s_src, im_s_dest), (hs_tile, hs_s_src, hs_s_dest)\
                in zip(tile_iterator(im,blocksize=N_sub,
                                     padsize=Npads,
                                     mode = mode),\
                    tile_iterator(psfs, blocksize=N_sub,
                                  padsize=Npads,
                                  mode = mode)):

                res_tile, plan = _convolve_spatial2(im_tile.copy(),
                                                    hs_tile.copy(),
                                                    mode=mode,
                                                    pad_factor=pad_factor,
                                                    return_plan=True,
                                                    plan=plan,
                                                    grid_dim=grid_dim_sub)

                res[im_s_src] = res_tile[im_s_dest]
            return res

        else:
            raise NotImplementedError()
コード例 #4
0
def convolve_spatial3(im,
                      psfs,
                      mode="constant",
                      grid_dim=None,
                      sub_blocks=None,
                      pad_factor=2,
                      plan=None,
                      return_plan=False,
                      verbose=False):
    """
    GPU accelerated spatial varying convolution of an 3d image with a
    (Gz, Gy, Gx) grid of psfs assumed to be equally spaced within the image

    the input image im is subdivided into (Gz, Gy,Gx) blocks, each block is
    convolved with the corresponding psf and linearly interpolated to give the
    final result

    The psfs can be given either in

    A) Stackmode

    psfs.shape =  (Gz, Gy, Gx, Hz, Hy, Hx)
    then psfs[k,j,i] is the psf at the center of each block (i,j,k) in the image

    B) Flatmode

    psfs.shape = im.shape
    then the psfs are assumed to be definied on the gridpoints of the images itself
    in this case grid_dim = (Gz,Gy,Gx) has to be given

    as of now each image dimension has to be divisible by the grid dim, i.e.
    ::
        Nx % Gx == 0
        Ny % Gy == 0
        Nz % Gz == 0


    GPU Memory consumption is of order 8*Nx*Ny*Nz
    If not enough GPU memory is available, consider using
    sub_blocks = (n,m,l)
    then the operation is carried out in a tiled fashion reducing
    memory consumption to 8*Nx*Ny*(1/n+2/Gx)*(1/m+2/Gy)*(1/l+2/Gz)
    (so there is no much use if n>Gx/2...)
    Example
    -------


    im = np.zeros((64,64,64))
    im[::10,::10,::10] = 1.

    # Stackmode
    psfs = np.ones((8,8,8,4,4,4))
    res = convolve_spatial3(im, psfs, mode = "wrap")

    # Flatmode
    _Xs = np.meshgrid(*(np.arange(64),)*2)
    psfs = np.prod([np.clip(np.sin(2*np.pi*_X/8),0,1) for _X in _Xs],axis=0)
    res = convolve_spatial2(im, psfs, grid_dim = (16,16,16))


    Parameters
    ----------
    im: ndarray
        the image to convolve
    psfs: ndarray
        the (Gx,Gy) psf grid, either of shape (Gx,Gy, Hy, Hx) or im.shape

    mode: string, optional
        Padding mode. Can be "constant", "wrap", "edge", or "reflect".
    grid_dim: tuple, optional
        the (Gy,Gx) grid dimension, has to be provided if psfs.shape = im.shape

    sub_blocks: tuple, optional
        tiling mode, give e.g. (2,2) to sequentially operate on quadratnts
    pad_factor: int
        the factor of its size each block get tiled, use pad_factor=2 if the psfs
        are well localized, use pad_factor = 3 if not (e.g. if you experience blocking)_

    plan: fft_plan, optional
        when given use this as the fft plan
    return_plan: bool, optional
        return (res, plan) with plan being the fft plan for further use

    Returns
    -------
    res: ndarray
        the convolved image



    """

    ndim = im.ndim

    if ndim != 3:
        raise ValueError("wrong dimensions of input!")

    if grid_dim:
        if psfs.shape != im.shape:
            raise ValueError("if grid_dim is set, then im.shape = hs.shape !")
    else:
        if not psfs.ndim == 2 * ndim:
            raise ValueError(
                "wrong dimensions of psf grid! should be (Gz,Gy,Gx,Nz,Ny,Nx)")

    if grid_dim:
        Gs = grid_dim
    else:
        Gs = psfs.shape[:ndim]

    if not np.all([n % g == 0 for n, g in zip(im.shape, Gs)]):
        raise NotImplementedError(
            "shape of image has to be divisible by Gx Gy  = %s shape mismatch"
            % (str(psfs.shape[:2])))

    if sub_blocks == None:
        return _convolve_spatial3(im,
                                  psfs,
                                  mode=mode,
                                  pad_factor=pad_factor,
                                  plan=plan,
                                  return_plan=return_plan,
                                  grid_dim=grid_dim)
    else:
        if not np.all([g % n == 0 for n, g in zip(sub_blocks, Gs)]):
            raise ValueError(
                "psf grid dimension has to be divisible corresponding n_blocks"
            )

        N_sub = [n // s for n, s in zip(im.shape, sub_blocks)]
        Nblocks = [n // g for n, g in zip(im.shape, Gs)]
        Npads = [n * (s > 1) for n, s in zip(Nblocks, sub_blocks)]
        grid_dim_sub = [g // s + 2 * (s > 1) for g, s in zip(Gs, sub_blocks)]

        if grid_dim:
            res = np.empty(im.shape, np.float32)
            plan = None
            for i, ((im_tile, im_s_src, im_s_dest), (hs_tile, hs_s_src, hs_s_dest)) \
                    in enumerate(zip(tile_iterator(im, blocksize=N_sub,
                                                   padsize=Npads,
                                                   mode=mode,
                                                   verbose=verbose), \
                                     tile_iterator(psfs, blocksize=N_sub,
                                                   padsize=Npads,
                                                   mode=mode,
                                                   verbose=verbose
                                                   ))):

                if verbose:
                    print("convolve_spatial3 ... %s\t/ %s" %
                          (i + 1, np.prod(sub_blocks)))

                res_tile, plan = _convolve_spatial3(im_tile.copy(),
                                                    hs_tile.copy(),
                                                    mode=mode,
                                                    pad_factor=pad_factor,
                                                    return_plan=True,
                                                    plan=plan,
                                                    grid_dim=grid_dim_sub)

                res[im_s_src] = res_tile[im_s_dest]
            return res

        else:
            raise NotImplementedError(
                "sub_blocks only implemented for Flatmode")