Exemplo n.º 1
0
def local_contrast_normalise(s, n=7, c=None):
    """Local contrast normalisation of an image.

    Perform local contrast normalisation :cite:`jarret-2009-what` of
    an image, consisting of subtraction of the local mean and division
    by the local norm. The original image can be reconstructed from the
    contrast normalised image as (`snrm` * `scn`) + `smn`.

    Parameters
    ----------
    s : array_like
      Input image or array of images.
    n : int, optional (default 7)
      The size of the local region used for normalisation is :math:`2n+1`.
    c : float, optional (default None)
      The smallest value that can be used in the divisive normalisation.
      If `None`, this value is set to the mean of the local region norms.

    Returns
    -------
    scn : ndarray
      Contrast normalised image(s)
    smn : ndarray
      Additive normalisation correction
    snrm : ndarray
      Multiplicative normalisation correction
    """

    # Construct region weighting filter
    N = 2 * n + 1
    g = gaussian((N, N), sd=1.0)
    # Compute required image padding
    pd = ((n, n), ) * 2
    if s.ndim > 2:
        g = g[..., np.newaxis]
        pd += ((0, 0), )
    sp = np.pad(s, pd, mode='symmetric')
    # Compute local mean and subtract from image
    smn = np.roll(sla.fftconv(g, sp), (-n, -n), axis=(0, 1))
    s1 = sp - smn
    # Compute local norm
    snrm = np.roll(np.sqrt(np.clip(sla.fftconv(g, s1**2), 0.0, np.inf)),
                   (-n, -n),
                   axis=(0, 1))
    # Set c parameter if not specified
    if c is None:
        c = np.mean(snrm, axis=(0, 1), keepdims=True)
    # Divide mean-subtracted image by corrected local norm
    snrm = np.maximum(c, snrm)
    s2 = s1 / snrm
    # Return contrast normalised image and normalisation components
    return s2[n:-n, n:-n], smn[n:-n, n:-n], snrm[n:-n, n:-n]
Exemplo n.º 2
0
def local_contrast_normalise(s, n=7, c=None):
    """
    Perform local contrast normalisation :cite:`jarret-2009-what` of
    an image, consisting of subtraction of the local mean and division
    by the local norm. The original image can be reconstructed from the
    contrast normalised image as (`snrm` * `scn`) + `smn`.

    Parameters
    ----------
    s : array_like
      Input image or array of images.
    n : int, optional (default 7)
      The size of the local region used for normalisation is :math:`2n+1`.
    c : float, optional (default None)
      The smallest value that can be used in the divisive normalisation.
      If `None`, this value is set to the mean of the local region norms.

    Returns
    -------
    scn : ndarray
      Contrast normalised image(s)
    smn : ndarray
      Additive normalisation correction
    snrm : ndarray
      Multiplicative normalisation correction
    """

    # Construct region weighting filter
    N = 2 * n + 1
    g = gaussian((N, N), sd=1.0)
    # Compute required image padding
    pd = ((n, n),) * 2
    if s.ndim > 2:
        g = g[..., np.newaxis]
        pd += ((0, 0),)
    sp = np.pad(s, pd, mode='symmetric')
    # Compute local mean and subtract from image
    smn = np.roll(sla.fftconv(g, sp), (-n, -n), axis=(0, 1))
    s1 = sp - smn
    # Compute local norm
    snrm = np.roll(np.sqrt(np.clip(sla.fftconv(g, s1**2), 0.0, np.inf)),
                   (-n, -n), axis=(0, 1))
    # Set c parameter if not specified
    if c is None:
        c = np.mean(snrm, axis=(0, 1), keepdims=True)
    # Divide mean-subtracted image by corrected local norm
    snrm = np.maximum(c, snrm)
    s2 = s1 / snrm
    # Return contrast normalised image and normalisation components
    return s2[n:-n, n:-n], smn[n:-n, n:-n], snrm[n:-n, n:-n]
Exemplo n.º 3
0
 def test_10(self):
     N = 64
     M = 4
     Nd = 8
     D = np.random.randn(Nd, Nd, M)
     X0 = np.zeros((N, N, M))
     xr = np.random.randn(N, N, M)
     xp = np.abs(xr) > 3
     X0[xp] = np.random.randn(X0[xp].size)
     S = np.sum(sl.fftconv(D, X0), axis=2)
     lmbda = 1e-4
     rho = 1e-1
     opt = cbpdn.ConvBPDN.Options({
         'Verbose': False,
         'MaxMainIter': 500,
         'RelStopTol': 1e-3,
         'rho': rho,
         'AutoRho': {
             'Enabled': False
         }
     })
     b = cbpdn.ConvBPDN(D, S, lmbda, opt)
     b.solve()
     X1 = b.Y.squeeze()
     assert sl.rrs(X0, X1) < 5e-5
     Sr = b.reconstruct().squeeze()
     assert sl.rrs(S, Sr) < 1e-4
Exemplo n.º 4
0
 def test_27(self):
     x = np.random.randn(5,)
     y = np.zeros((12,))
     y[4] = 1.0
     xy0 = convolve(y, x)
     xy1 = linalg.fftconv(x, y, axes=(0,), origin=(2,))
     assert np.allclose(xy0, xy1)
Exemplo n.º 5
0
 def test_22(self):
     N = 32
     M = 4
     Nd = 8
     D = np.random.randn(Nd, Nd, M)
     D /= np.sqrt(np.sum(D**2, axis=(0, 1)))
     X0 = np.zeros((N, N, M))
     xr = np.random.randn(N, N, M)
     xp = np.abs(xr) > 3
     X0[xp] = np.random.randn(X0[xp].size)
     S = np.sum(sl.fftconv(D, X0), axis=2)
     lmbda = 1e-3
     opt = cbpdn.ConvBPDN.Options({'Verbose': False, 'MaxMainIter': 500,
                      'RelStopTol': 1e-5, 'rho': 5e-1,
                      'AutoRho': {'Enabled': False}})
     bp = cbpdn.ConvBPDN(D, S, lmbda, opt)
     Xp = bp.solve()
     epsilon = np.linalg.norm(bp.reconstruct(Xp).squeeze() - S)
     opt = cbpdn.ConvMinL1InL2Ball.Options({'Verbose': False,
                               'MaxMainIter': 500, 'RelStopTol': 1e-5,
                               'rho': 2e2, 'RelaxParam': 1.0,
                               'AutoRho': {'Enabled': False}})
     bc = cbpdn.ConvMinL1InL2Ball(D, S, epsilon=epsilon, opt=opt)
     Xc = bc.solve()
     assert np.linalg.norm(Xp - Xc) / np.linalg.norm(Xp) < 1e-3
     assert(np.abs(np.linalg.norm(Xp.ravel(), 1) -
                   np.linalg.norm(Xc.ravel(), 1)) < 1e-3)
Exemplo n.º 6
0
def run_cbpdn_gpu(D, sl, sh, lmbda, test_blob=None, opt=None):
    """Run GPU version of CBPDN.  Only supports grayscale images."""
    assert _cfg.TEST.DATASET.GRAY, 'Only grayscale images are supported'
    assert cucbpdn is not None, 'GPU CBPDN is not supported'
    opt = cbpdn.ConvBPDN.Options(opt)
    if test_blob is None:
        test_blob = sl + sh
    fnc, psnr = 0., 0.
    for idx in range(test_blob.shape[-1]):
        X = cucbpdn.cbpdn(D, sh[..., idx].squeeze(), lmbda, opt=opt)
        shr = np.sum(spl.fftconv(D, X), axis=2)
        dfd = linalg.norm(shr.ravel() - sh[..., idx].ravel())
        rl1 = linalg.norm(X.ravel(), 1)
        obj = dfd + lmbda * rl1
        fnc += obj
        imgr = sl[..., idx] + shr
        psnr += sm.psnr(imgr, test_blob[..., idx].squeeze(), rng=1.)
    psnr /= test_blob.shape[-1]
    if _cfg.VERBOSE:
        print('.', end='', flush=True)
    return fnc, psnr
Exemplo n.º 7
0
    }
})
"""
Construct :class:`.admm.cbpdn.AddMaskSim` wrapper for :class:`.admm.cbpdn.ConvBPDNGradReg` and solve via wrapper. If the ``sporco-cuda`` extension is installed and a GPU is available, use the CUDA implementation of this combination.
"""

if cuda.device_count() > 0:
    opt['L1Weight'] = wl1
    opt['GradWeight'] = wgr
    ams = None
    print('%s GPU found: running CUDA solver' % cuda.device_name())
    tm = util.Timer()
    with sys_pipes(), util.ContextTimer(tm):
        X = cuda.cbpdngrdmsk(Di, imgwp, mskp, lmbda, mu, opt)
    t = tm.elapsed()
    imgr = crop(np.sum(linalg.fftconv(Di, X), axis=-1))
else:
    opt['L1Weight'] = wl1i
    opt['GradWeight'] = wgri
    ams = cbpdn.AddMaskSim(cbpdn.ConvBPDNGradReg,
                           Di,
                           imgwp,
                           mskp,
                           lmbda,
                           mu,
                           opt=opt)
    X = ams.solve().squeeze()
    t = ams.timer.elapsed('solve')
    imgr = crop(ams.reconstruct().squeeze())
"""
Display solve time and reconstruction performance.
Exemplo n.º 8
0
    print('%s GPU found: running CUDA solver' % cuda.device_name())
    tm = util.Timer()
    with sys_pipes(), util.ContextTimer(tm):
        X = cuda.cbpdn(D, sh, lmbda, opt)
    t = tm.elapsed()
else:
    print('GPU not found: running Python solver')
    c = cbpdn.ConvBPDN(D, sh, lmbda, opt)
    X = c.solve().squeeze()
    t = c.timer.elapsed('solve')
print('Solve time: %.2f s' % t)
"""
Reconstruct the image from the sparse representation.
"""

shr = np.sum(spl.fftconv(D, X), axis=2)
imgr = sl + shr
print("Reconstruction PSNR: %.2fdB\n" % spm.psnr(img, imgr))
"""
Display representation and reconstructed image.
"""

fig = plot.figure(figsize=(14, 14))
plot.subplot(2, 2, 1)
plot.imview(sl, title='Lowpass component', fig=fig)
plot.subplot(2, 2, 2)
plot.imview(np.sum(abs(X), axis=2).squeeze(),
            cmap=plot.cm.Blues,
            title='Main representation',
            fig=fig)
plot.subplot(2, 2, 3)
Exemplo n.º 9
0
 def test_26(self):
     x = np.array([[0, 1], [2, 3]])
     y = np.array([[4, 5], [6, 7]])
     xy = np.array([[38, 36], [30, 28]])
     assert np.allclose(linalg.fftconv(x, y), xy)
Exemplo n.º 10
0
 def test_26(self):
     x = np.array([[0, 1], [2, 3]])
     y = np.array([[4, 5], [6, 7]])
     xy = np.array([[38, 36], [30, 28]])
     assert np.allclose(linalg.fftconv(x, y), xy)
Exemplo n.º 11
0
    with sys_pipes(), util.ContextTimer(tm):
        X = cuda.cbpdngrd(D, img, lmbda, mu, opt)
    t = tm.elapsed()
else:
    print('GPU not found: running Python solver')
    c = cbpdn.ConvBPDNGradReg(D, img, lmbda, mu, opt)
    X = c.solve().squeeze()
    t = c.timer.elapsed('solve')
print('Solve time: %.2f s' % t)


"""
Reconstruct the image from the sparse representation.
"""

imgr = np.sum(spl.fftconv(D, X), axis=2)
print("Reconstruction PSNR: %.2fdB\n" % spm.psnr(img, imgr))


"""
Display representation and reconstructed image.
"""

fig = plot.figure(figsize=(14, 14))
plot.subplot(2, 2, 1)
plot.imview(X[..., 0].squeeze(), title='Lowpass component', fig=fig)
plot.subplot(2, 2, 2)
plot.imview(np.sum(abs(X[..., 1:]), axis=2).squeeze(),
            cmap=plot.cm.Blues, title='Main representation', fig=fig)
plot.subplot(2, 2, 3)
plot.imview(imgr, title='Reconstructed image', fig=fig)
Exemplo n.º 12
0
else:
    id = select_device_by_load()
    info = gpu_info()
    if info:
        print('Running on GPU %d (%s)\n' % (id, info[id].name))

b = pdcsc.ConvProdDictBPDN(np2cp(D), np2cp(B), np2cp(shc), lmbda, opt, dimK=0)
X = cp2np(b.solve())
print("ConvProdDictBPDN solve time: %.2fs" % b.timer.elapsed('solve'))


"""
Compute partial and full reconstructions from sparse representation $X$ with respect to convolutional dictionary $D$ and standard dictionary $B$. The partial reconstructions are $DX$ and $XB$, and the full reconstruction is $DXB$.
"""

DX = sl.fftconv(D[..., np.newaxis, np.newaxis, :], X)
XB = sl.dot(B, X, axis=2)
shr = cp2np(b.reconstruct().squeeze())
imgr = slc + shr
print("Reconstruction PSNR: %.2fdB\n" % sm.psnr(img, imgr))


"""
Display original and reconstructed images.
"""

gamma = lambda x, g: np.sign(x) * (np.abs(x)**g)

fig, ax = plot.subplots(nrows=2, ncols=2, figsize=(14, 14))
plot.imview(img, title='Original image', ax=ax[0, 0], fig=fig)
plot.imview(slc, title='Lowpass component', ax=ax[0, 1], fig=fig)
Exemplo n.º 13
0
        'Enabled': False,
        'StdResiduals': False
    }
})
"""
Construct :class:`.admm.cbpdn.AddMaskSim` wrapper for :class:`.admm.cbpdn.ConvBPDN` and solve via wrapper. This example could also have made use of :class:`.admm.cbpdn.ConvBPDNMaskDcpl` (see example `cbpdn_md_gry`), which has similar performance in this application, but :class:`.admm.cbpdn.AddMaskSim` has the advantage of greater flexibility in that the wrapper can be applied to a variety of CSC solver objects. If the ``sporco-cuda`` extension is installed and a GPU is available, use the CUDA implementation of this combination.
"""

if cuda.device_count() > 0:
    ams = None
    print('%s GPU found: running CUDA solver' % cuda.device_name())
    tm = util.Timer()
    with sys_pipes(), util.ContextTimer(tm):
        X = cuda.cbpdnmsk(D, sh, mskp, lmbda, opt)
    t = tm.elapsed()
    imgr = crop(sl + np.sum(linalg.fftconv(D, X), axis=-1))
else:
    ams = cbpdn.AddMaskSim(cbpdn.ConvBPDN, D, sh, mskp, lmbda, opt=opt)
    X = ams.solve()
    t = ams.timer.elapsed('solve')
    imgr = crop(sl + ams.reconstruct().squeeze())
"""
Display solve time and reconstruction performance.
"""

print("AddMaskSim wrapped ConvBPDN solve time: %.2fs" % t)
print("Corrupted image PSNR: %5.2f dB" % metric.psnr(img, imgw))
print("Recovered image PSNR: %5.2f dB" % metric.psnr(img, imgr))
"""
Display reference, test, and reconstructed image
"""
Exemplo n.º 14
0
                    'rho': 5e1*lmbda + 1e-1, 'AutoRho': {'Enabled': False,
                    'StdResiduals': False}})


"""
Construct :class:`.admm.cbpdn.AddMaskSim` wrapper for :class:`.admm.cbpdn.ConvBPDN` and solve via wrapper. This example could also have made use of :class:`.admm.cbpdn.ConvBPDNMaskDcpl` (see example `cbpdn_md_gry`), which has similar performance in this application, but :class:`.admm.cbpdn.AddMaskSim` has the advantage of greater flexibility in that the wrapper can be applied to a variety of CSC solver objects. If the ``sporco-cuda`` extension is installed and a GPU is available, use the CUDA implementation of this combination.
"""

if cuda.device_count() > 0:
    ams = None
    print('%s GPU found: running CUDA solver' % cuda.device_name())
    tm = util.Timer()
    with sys_pipes(), util.ContextTimer(tm):
        X = cuda.cbpdnmsk(D, sh, mskp, lmbda, opt)
    t = tm.elapsed()
    imgr = crop(sl + np.sum(linalg.fftconv(D, X), axis=-1))
else:
    ams = cbpdn.AddMaskSim(cbpdn.ConvBPDN, D, sh, mskp, lmbda, opt=opt)
    X = ams.solve()
    t = ams.timer.elapsed('solve')
    imgr = crop(sl + ams.reconstruct().squeeze())


"""
Display solve time and reconstruction performance.
"""

print("AddMaskSim wrapped ConvBPDN solve time: %.2fs" % t)
print("Corrupted image PSNR: %5.2f dB" % metric.psnr(img, imgw))
print("Recovered image PSNR: %5.2f dB" % metric.psnr(img, imgr))
Exemplo n.º 15
0

"""
Construct :class:`.admm.cbpdn.AddMaskSim` wrapper for :class:`.admm.cbpdn.ConvBPDNGradReg` and solve via wrapper. If the ``sporco-cuda`` extension is installed and a GPU is available, use the CUDA implementation of this combination.
"""

if cuda.device_count() > 0:
    opt['L1Weight'] = wl1
    opt['GradWeight'] = wgr
    ams = None
    print('%s GPU found: running CUDA solver' % cuda.device_name())
    tm = util.Timer()
    with sys_pipes(), util.ContextTimer(tm):
        X = cuda.cbpdngrdmsk(Di, imgwp, mskp, lmbda, mu, opt)
    t = tm.elapsed()
    imgr = crop(np.sum(linalg.fftconv(Di, X), axis=-1))
else:
    opt['L1Weight'] = wl1i
    opt['GradWeight'] = wgri
    ams = cbpdn.AddMaskSim(cbpdn.ConvBPDNGradReg, Di, imgwp, mskp, lmbda, mu,
                           opt=opt)
    X = ams.solve().squeeze()
    t = ams.timer.elapsed('solve')
    imgr = crop(ams.reconstruct().squeeze())


"""
Display solve time and reconstruction performance.
"""

print("AddMaskSim wrapped ConvBPDN solve time: %.2fs" % t)