多元优化scipy.optimize公司输入解析

2024-09-28 01:28:23 发布

您现在位置:Python中文网/ 问答频道 /正文

rgb image

我将上面的rgb图像保存为tux.jpg。现在我想得到最接近这个图像的近似值,它是两个向量的外积,即A·BT。在

这是我的密码-

#load image to memory
import Image
im = Image.open('tux.jpg','r')
#save image to numpy array
import numpy as np
mat = np.asfarray(im.convert(mode='L')) # mat is a numpy array of dimension 354*300
msizex,msizey = mat.shape
x0 = np.sum(mat,axis=1)/msizex
y0 = np.sum(mat,axis=0)/msizey

X0 = np.concatenate((x0,y0)) # X0.shape is (654,)
# define error of outer product with respect to original image
def sumsquares(X):
    """ sum of squares - 
    calculates the difference between original and outer product

    input X is a 1D numpy array with the first 354 elements
    representing vector A and the rest 300 representing vector B.
    The error is obtained by subtracting the trial  $A\cdot B^T$ 
    from the original and then adding the square of all entries in 
    the matrix.
    """
    assert X.shape[0] == msizex+msizey
    x = X0[:msizex]
    y = X0[msizex:]
    return np.sum(
        (
        np.outer(x,y) - mat
        )**2
    )
#import minimize
from scipy.optimize import minimize
res = minimize(sumsquares, X0,
               method='nelder-mead',
               options={'disp':True}
)
xout = res.x[:msizex]
yout = res.x[msizex:]
mout = np.outer(xout,yout)
imout= Image.fromarray(mout,mode='L')
imout.show()

{a2}结果是^。在

^{pr2}$

我觉得这还不够好。有什么办法可以改进吗?输出中的噪声甚至与原始图像中的结构长度不一样。我的猜测是算法无法通过。我如何调试或改进它?在

编辑1:我用代码创建了下面的图像

size = 256
mat0 = np.zeros((size,size))
mat0[size/4:3*size/4,size/4:3*size/4] = 1000
#mat0[size/4:3*size/4,] = 1000
#mat0[:3*size/4,size/4:] = 1000

im0 = Image.fromarray(mat0)
im0.show() 

这两条注释掉的行产生了另外两幅图像。这是我的实验结果-

    在正方形中间。 输入-square middle
    输出-相同 在中间带。 输入-band middle
    输出-square middle
  1. 东北部的白色区块 输入-north east
    输出-north west

虽然这比我预期的要好得多,但案例2和3最终还是错了。我希望minimize函数的参数能像我想的那样。在


Tags: ofthe图像imageimportnumpysizeis
1条回答
网友
1楼 · 发布于 2024-09-28 01:28:23

1)第一个图像的渲染问题似乎是从numpy数组到图像的转换中的一个问题。我通过运行:

imout = Image.fromarray(mout/np.max(mout)*255)

(即,将图像规格化为最大值255,并让它自动确定模式)。在

一般来说,检查一下图像.fromarray正在工作,比较imout.show公司()与

^{pr2}$

你应该得到同样的结果。顺便说一句,这么做,我就把其他3个案子都搞错了。在

2)第二,主要问题是晚礼服.png是不可能用两个一维向量的外积来重建具有如此详细结构的图像。在

(这通常适用于简单的图像,如上面所示的块状图像,但对于对称性较少、细节较多的图像则不适用)。在

为了证明这一点:

  • 现有的矩阵分解技术允许将矩阵重构为两个低秩矩阵M=AB的乘积,例如sklearn.decomposition.NMF

  • 在这种情况下,将A和B的等级设置为1相当于您的问题(使用不同的优化技术)。

  • 使用下面的代码,您可以很容易地看到,当n_分量=1时(相当于两个一维向量的外积),得到的重建矩阵看起来与您的方法输出的矩阵非常相似,并且n_分量越大,重建效果越好。

再现性:

import matplotlib.pyplot as plt
from sklearn.decomposition import NMF

nmf = NMF(n_components=20)
prj = nmf.fit_transform(mat)

out = prj.dot(nmf.components_)
out = np.asarray(out, dtype=float)

imout = Image.fromarray(out)
imout.show()

举例来说,这是具有1个分量的NMF重建(这正是两个一维向量之间的外积):

NMF reconstruction with 1 component, equivalent to outer product of 2 vectors

有两个组件:

2 components

这是由20个组件组成的NMF重建。在

NMF reconstruction with 20 components, equivalent to the sum of 20 1-D vector outer products)

这清楚地表明,一个单一的1-D外部产品是不够的,为这个图像。但是它对块状图像有效。在

如果你不局限于向量的外积,那么矩阵因子分解是一种替代方法。顺便说一句,存在着大量的矩阵分解技术。sklearn的另一个选择是SVD。在

3)最后,x0和y0中可能存在缩放问题。注意np.外部(x0,y0)比mat元素高一个数量级。在

虽然我在提供的代码中仍然得到了3个块状示例的良好结果,但一般来说,在计算平方差时,使用可比较的比例是一个很好的实践。例如,您可能需要缩放x0和y0,以便np.外部可与mat相提并论。在

相关问题 更多 >

    热门问题