问题描述
我正在尝试为我最后一年的项目编写压缩感知演示,但在使用套索算法时图像重建效果不佳。我依赖以下内容作为参考:http://www.pyrunner.com/weblog/2016/05/26/compressed-sensing-python/ 但是我的代码有一些差异:
- 我使用 scikit-learn 来执行套索优化(基础追踪),而不是使用 cvxpy 来执行具有等式约束的 l_1 最小化,如本文所述。
- 我以不同的方式/更简单地构建 psi,测试似乎表明它是正确的。
- 我使用不同的包来读取和写入图像。
import numpy as np
import scipy.fftpack as spfft
import scipy.ndimage as spimg
import imageio
from sklearn.linear_model import Lasso
x_orig = imageio.imread('gt40.jpg',pilmode='L') # read in grayscale
x = spimg.zoom(x_orig,0.2) #zoom for speed
ny,nx = x.shape
k = round(nx * ny * 0.5) #50% sample
ri = np.random.choice(nx * ny,k,replace=False)
y = x.T.flat[ri] #y is the measured sample
# y = np.expand_dims(y,axis=1) ---- this doesn't seem to make a difference,was presumably required with cvxpy
psi = spfft.idct(np.identity(nx*ny),norm='ortho',axis=0) #my construction of psi
# psi = np.kron(
# spfft.idct(np.identity(nx),axis=0),# spfft.idct(np.identity(ny),axis=0)
# )
# psi = 2*np.random.random_sample((nx*ny,nx*ny)) - 1
theta = psi[ri,:] #equivalent to phi*psi
lasso = Lasso(alpha=0.001,max_iter=10000)
lasso.fit(theta,y)
s = np.array(lasso.coef_)
x_recovered = psi@s
x_recovered = x_recovered.reshape(nx,ny).T
x_recovered_final = x_recovered.astype('uint8') #recovered image is float64 and has negative values..
imageio.imwrite('gt40_recovered.jpg',x_recovered_final)
不幸的是,我还不允许发布图像,所以这里是原始缩放图像的链接,用套索恢复的图像和用 cvxpy 恢复的图像(稍后描述): https://imgur.com/a/LROSug6
正如您所看到的,不仅恢复不佳,而且图像完全损坏 - 颜色似乎是负的,并且 50% 样本的细节丢失了。我想我已经设法将问题追溯到套索回归 - 它返回一个向量,当逆变换时,其值不一定在图像预期的 0-255 范围内。所以从 dtype float64 到 uint8 的转换是相当随机的(例如 -55 变成 255-55=200)。
在此之后,我尝试更换套索以进行与文章中相同的优化(使用 cvxpy 最小化受 theta*s=y 约束的 l_1 范数):
import cvxpy as cvx
x_orig = imageio.imread('gt40.jpg',0.2)
ny,nx = x.shape
k = round(nx * ny * 0.5)
ri = np.random.choice(nx * ny,replace=False)
y = x.T.flat[ri]
psi = spfft.idct(np.identity(nx*ny),axis=0)
theta = psi[ri,:] #equivalent to phi*psi
#NEW CODE STARTS:
vx = cvx.Variable(nx * ny)
objective = cvx.Minimize(cvx.norm(vx,1))
constraints = [theta@vx == y]
prob = cvx.Problem(objective,constraints)
result = prob.solve(verbose=True)
s = np.array(vx.value).squeeze()
x_recovered = psi@s
x_recovered = x_recovered.reshape(nx,ny).T
x_recovered_final = x_recovered.astype('uint8')
imageio.imwrite('gt40_recovered_altopt.jpg',x_recovered_final)
这花了将近 6 个小时,但最终我得到了一个比较满意的结果。但是,如果可能的话,我想演示套索。任何帮助使套索返回适当的值或以某种方式适当地转换其结果的任何帮助将不胜感激。
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)