PCA降维用于分类

我正在对从CNN不同层提取的特征使用主成分分析(PCA)。我已经从这里下载了降维工具箱。

我总共有11232张训练图像,每张图像的特征维度为6532。因此,特征矩阵的形状为11232x6532。如果我想保留前90%的特征,我可以轻松做到这一点,并且使用SVM对降维后的数据进行训练,准确率为81.73%,这还算不错。然而,当我尝试使用测试数据时,测试数据有2408张图像,每张图像的特征维度为6532。因此,测试数据的特征矩阵形状为2408x6532。在这种情况下,前90%特征的输出结果不正确,显示为2408x2408,并且测试准确率为25%。在不使用降维的情况下,训练准确率为82.17%,测试准确率为79%。
更新:其中X是数据,no_dims是输出所需的维度数。这个PCA函数的输出是变量mappedX和结构mapping

% Make sure data is zero mean    mapping.mean = mean(X, 1);    X = bsxfun(@minus, X, mapping.mean);    % Compute covariance matrix    if size(X, 2) < size(X, 1)        C = cov(X);    else        C = (1 / size(X, 1)) * (X * X');        % if N>D, we better use this matrix for the eigendecomposition    end    % Perform eigendecomposition of C    C(isnan(C)) = 0;    C(isinf(C)) = 0;    [M, lambda] = eig(C);    % Sort eigenvectors in descending order    [lambda, ind] = sort(diag(lambda), 'descend');    if no_dims < 1        no_dims = find(cumsum(lambda ./ sum(lambda)) >= no_dims, 1, 'first');        disp(['Embedding into ' num2str(no_dims) ' dimensions.']);    end    if no_dims > size(M, 2)        no_dims = size(M, 2);        warning(['Target dimensionality reduced to ' num2str(no_dims) '.']);    end    M = M(:,ind(1:no_dims));    lambda = lambda(1:no_dims);    % Apply mapping on the data    if ~(size(X, 2) < size(X, 1))        M = bsxfun(@times, X' * M, (1 ./ sqrt(size(X, 1) .* lambda))');     % normalize in order to get eigenvectors of covariance matrix    end    mappedX = X * M;    % Store information for out-of-sample extension    mapping.M = M;    mapping.lambda = lambda;

根据你的建议,我已经计算了训练数据的向量。

numberOfDimensions = round(0.9*size(Feature,2));[mapped_data, mapping] = compute_mapping(Feature, 'PCA', numberOfDimensions);

然后使用相同的向量处理测试数据:

mappedX_test = Feature_test * mapping.M;

准确率仍然是32%

通过进行减法操作解决了问题:

Y = bsxfun(@minus, Feature_test, mapping.mean);mappedX_test = Y * mapping.M;

回答:

看起来你是在对训练数据和测试数据分别进行降维。在训练过程中,你应该记住训练样本的主成分得分或基向量。请记住,你是在基于训练数据寻找数据的新表示,使用一组新的正交轴。在测试过程中,你需要重复训练数据的相同过程,因为你是在相对于这些基向量表示数据。因此,你应该使用训练数据的基向量来降低数据维度。你之所以得到2408 x 2408的矩阵,是因为你在测试样本上执行PCA,而你无法生成超过矩阵秩的基向量(即2408)。

保留训练阶段的基向量,在测试阶段进行分类时,必须使用训练阶段的相同基向量。请记住,在PCA中,你必须在降维之前通过减去均值来中心化数据。在你的代码中,我们注意到基向量存储在mapping.M中,相关的均值向量存储在mapping.mean中。在测试阶段,确保使用训练阶段的mapping.mean对测试数据进行均值减法:

Y = bsxfun(@minus, Feature_test, mapping.mean);

完成这一步后,最后进行数据降维:

mappedX_test = Y * mapping.M;

Related Posts

L1-L2正则化的不同系数

我想对网络的权重同时应用L1和L2正则化。然而,我找不…

使用scikit-learn的无监督方法将列表分类成不同组别,有没有办法?

我有一系列实例,每个实例都有一份列表,代表它所遵循的不…

f1_score metric in lightgbm

我想使用自定义指标f1_score来训练一个lgb模型…

通过相关系数矩阵进行特征选择

我在测试不同的算法时,如逻辑回归、高斯朴素贝叶斯、随机…

可以将机器学习库用于流式输入和输出吗?

已关闭。此问题需要更加聚焦。目前不接受回答。 想要改进…

在TensorFlow中,queue.dequeue_up_to()方法的用途是什么?

我对这个方法感到非常困惑,特别是当我发现这个令人费解的…

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注