Python 高维数据的自动编码器

Python 高维数据的自动编码器,python,theano,dimensionality-reduction,autoencoder,Python,Theano,Dimensionality Reduction,Autoencoder,我正在做一个项目,在这个项目中,我需要降低我的观察结果的维度,并且仍然能够对它们进行有意义的表示。出于许多原因,强烈建议使用自动编码器,但我不太确定这是最好的方法 我有1400个样本的维数~60000,这太高了,我试图将它们的维数降低到原始维数的10%。我正在使用theano自动编码器,它的成本似乎一直在30000左右(这是非常高的)。我尝试过增加历次次数或降低学习率,但都没有成功。我不是自动编码器方面的专家,所以我不知道如何从这里开始,或者什么时候停止尝试 我还可以运行其他测试,但在继续之前,

我正在做一个项目,在这个项目中,我需要降低我的观察结果的维度,并且仍然能够对它们进行有意义的表示。出于许多原因,强烈建议使用自动编码器,但我不太确定这是最好的方法

我有1400个样本的维数~60000,这太高了,我试图将它们的维数降低到原始维数的10%。我正在使用theano自动编码器,它的成本似乎一直在30000左右(这是非常高的)。我尝试过增加历次次数或降低学习率,但都没有成功。我不是自动编码器方面的专家,所以我不知道如何从这里开始,或者什么时候停止尝试

我还可以运行其他测试,但在继续之前,我希望您能提供一些信息

  • 您是否认为数据集太小(我可以再添加600个样本,总共约2000个)

  • 你认为使用堆叠式自动编码器会有帮助吗

  • 我是否应该继续调整参数(时代和学习率)

由于数据集是一组图片,我试图将自动编码器的重建可视化,我得到的只是每个样本的相同输出。这意味着,给定输入,autoencoder会尝试重建输入,但我得到的是任何输入的相同(几乎完全相同)图像(这看起来像是数据集中所有图像的平均值)。这意味着内部表示不够好,因为自动编码器无法从中重建图像

数据集:1400-2000张扫描书籍(包括封面)的图像,每个图像约为60000像素(转化为60000个元素的特征向量)。每个特征向量已在[0,1]中标准化,最初在[0255]中有值

问题:使用自动编码器降低维度(如果可能)

如果您需要任何额外的信息,或者如果我遗漏了一些可能有助于更好地理解问题的信息,请添加评论,我将很乐意帮助您帮助我=)


注释:我现在正在运行一个测试,在整个数据集上有更多的历元,并且我会更新我的文章,结果可能需要一段时间。

< P>没有必要把30000的代价看作是“高”,除非更多的关于这个问题的描述是已知的。例如,如果隐藏层的大小特别小,并且数据中几乎没有冗余,那么全局最小成本实际上可能在30000左右

如果培训前的成本为30000(即使用随机编码器和解码器权重),并且即使在一些培训后仍保持在该水平,则可能有问题

您应该期望在第一次更新后成本会降低(如果使用minibatch随机梯度下降,则每个历元将有许多更新)。随着隐藏层大小的增加,收敛成本也会降低


在这种情况下可能有帮助的其他技术包括(可以认为是通过重复应用随机噪声来人为增加训练数据集的大小)和将其正则化能力集中在编码器(您关心的部分)上的技术。两者都可以在Theano中实现,第一个是()。

自动编码器之所以有用,部分原因是它们可以学习非线性降维。然而,还有其他降维技术,它们比自动编码器快得多。扩散贴图是一种流行的贴图;局部线性嵌入是另一种。我在>200060K的维度数据(也包括图像)上使用了扩散贴图,它在一分钟内就能工作

下面是一个使用numpy等人的简单Python实现:

def diffusion_maps(data, d, eps=-1, t=1):
    """
    data is organized such that columns are points. so it's 60k x 2k for you
    d is the target dimension
    eps is the kernel bandwidth, estimated automatically if == -1
    t is the diffusion time, 1 is usually fine
    """

    from scipy.spatial import pdist, squareform
    from scipy import linalg as la
    import numpy as np

    distances = squareform(pdist(data.T))

    if eps == -1:
        # if a kernel bandwidth was not supplied,
        # just use the distance to the tenth-nearest neighbor
        k = 10
        nn = np.sort(distances)
        eps = np.mean(nn[:, k + 1])

    kernel = np.exp(-distances ** 2 / eps ** 2)
    one = np.ones(n_samples)
    p_a = np.dot(kernel, one)
    kernel_p = walk / np.outer(p_a, p_a)
    dd = np.dot(kernel_p, one) ** 0.5
    walk = kernel_p / np.outer(dd, dd)

    vecs, eigs, _ = la.svd(walk, full_matrices=False)
    vecs = vecs / vecs[:, 0][:, None]
    diffusion_coordinates = vecs[:, 1:d + 1].T * (eigs[1:d + 1][:, None] ** t)

    return diffusion_coordinates

扩散图的要点是,你在数据上形成一个随机游走,这样你就更有可能访问附近的点而不是远处的点。然后可以定义点之间的距离(扩散距离),这本质上是在所有可能路径上两点之间移动的平均概率。诀窍是这实际上非常容易计算;你所需要做的就是对一个矩阵进行对角化,然后使用它的特征向量将数据嵌入低维空间。在这种嵌入中,欧几里德距离是扩散距离,达到近似误差。

首先简单的事情…请注意,如果在60000维空间中只有1400个点,则可以而不损失,降维到尺寸你有没有考虑过其他降维技术,如主成分分析?我绝对在考虑,但我仍然想了解为什么自动编码器不起作用。所以我在这里说了一句话“丹尼尔说了什么”,因为你应该先尝试简单的事情,PCA将为您提供与单层自动编码器一样多的功能(您将无法进行更多的培训)。另一个建议是使用预先训练过的convnet,如您可以在sklearn theano中找到的,来选择最新的层之一,并在空间上折叠通道,给出每个书皮的大小签名
(n_通道,)
。这将捕获一些视觉信息。请您进一步解释什么是“n_样本”?此外,代码在赋值之前使用变量“walk”。你能澄清一下吗?谢谢。你能解释一下“n_样本和行走”变量吗?