【问题标题】:Autoencoders for high dimensional data高维数据的自动编码器
【发布时间】:2015-09-06 17:19:17
【问题描述】:

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

我有 1400 个尺寸约为 60,000 的样本,这太高了,我正在尝试将它们的维度降低到原始维度的 10%。我正在使用 theano 自动编码器 [Link],似乎成本一直在 30,000 左右(非常高)。我尝试增加 epoch 数或降低学习率,但均未成功。我不是自动编码器方面的大专家,所以我不确定如何从这里开始或何时停止尝试。

我还可以运行其他测试,但在继续之前,我想听听您的意见。

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

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

  • 我应该继续调整参数(时期和学习率)吗?

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

数据集: 1400 - 2000 张扫描书籍(包括封面)的图像,每张约 60.000 像素(转换为 60.000 个元素的特征向量)。每个特征向量都在 [0,1] 中进行了归一化,最初的值在 [0,255] 中。

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

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

注意:我目前正在对整个数据集进行更多时期的测试,我将根据结果更新我的帖子,不过可能需要一段时间。

【问题讨论】:

  • 您是否考虑过其他降维技术,例如主成分分析?
  • 我绝对在考虑这一点,但我仍然想了解为什么自动编码器不起作用。
  • 所以我在这里有一句话说“Daniel 所说的”,因为你应该先尝试简单的事情,PCA 无论如何都会像单层自动编码器一样为你做很多事情(你不会能够训练的远不止这些)。另一个建议是使用预训练的卷积网络,例如您可以在 sklearn-theano 中找到的,选择一个最新的层并在空间上折叠通道,为每本书封面提供大小为 (n_channels,) 的签名。这将捕获一些视觉信息。

标签: python theano dimensionality-reduction autoencoder


【解决方案1】:

自动编码器之所以有用,部分原因是它们可以学习非线性降维。然而,还有其他降维技术,它们比自动编码器快得多。扩散贴图是一种流行的贴图;局部线性嵌入是另一个。我已经在超过 2000 个 60k 维数据(也包括图像)上使用了扩散图,它可以在一分钟内完成。

这是一个使用 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

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

【讨论】:

  • 您能否进一步解释一下“n_samples”是什么?此外,代码在赋值之前使用变量“walk”。你能澄清一下吗?谢谢。
  • 你能解释一下“n_samples and walk”变量吗?
【解决方案2】:

没有理由将 30,000 的成本视为“高”,除非对情况的了解比问题中描述的更多。例如,如果隐藏层的大小特别小并且数据中几乎没有冗余,那么全局最低成本实际上可能在 30,000 左右。

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

您应该期望在第一次更新后成本会降低(如果您使用小批量随机梯度下降,每个 epoch 将有很多更新)。您还应该预期收敛成本会随着隐藏层大小的增加而降低。

在这种情况下可能会有所帮助的其他技术包括 denoising autoencoder(可以被认为是通过重复应用随机噪声人为地增加训练数据集的大小)和 contractive autoencoder,它专注于其正则化能力在编码器上,您关心的部分。两者都可以在 Theano 中实现,第一个是 subject of this tutorial (with code)。

【讨论】:

    【解决方案3】:

    先做简单的事情...请注意,如果您在 60,000 维空间中只有 1400 个点,那么您可以无损失,将维度减少到

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-03-07
      • 2020-01-23
      • 2018-02-07
      • 2019-10-01
      • 2021-07-20
      • 2021-10-14
      • 2021-12-20
      • 2021-11-12
      相关资源
      最近更新 更多