楼主: ReneeBK
818 1

【JavaScript】Principal component analysis (PCA) using JavaScript [推广有奖]

  • 1关注
  • 62粉丝

VIP

已卖:4900份资源

学术权威

14%

还不是VIP/贵宾

-

TA的文库  其他...

R资源总汇

Panel Data Analysis

Experimental Design

威望
1
论坛币
49655 个
通用积分
55.9937
学术水平
370 点
热心指数
273 点
信用等级
335 点
经验
57805 点
帖子
4005
精华
21
在线时间
582 小时
注册时间
2005-5-8
最后登录
2023-11-26

楼主
ReneeBK 发表于 2017-4-16 04:15:55 |AI写论文

+2 论坛币
k人 参与回答

经管之家送您一份

应届毕业生专属福利!

求职就业群
赵安豆老师微信:zhaoandou666

经管之家联合CDA

送您一个全额奖学金名额~ !

感谢您参与论坛问题回答

经管之家送您两个论坛币!

+2 论坛币
ml-pca

Principal component analysis (PCA)

Installation

$ npm install ml-pca

DocumentationLicense

MIT

本帖隐藏的内容

pca-master.zip (1.16 MB)


二维码

扫码加我 拉你入群

请注明:姓名-公司-职位

以便审核进群资格,未注明则拒绝


沙发
ReneeBK 发表于 2017-4-16 04:16:25
  1. 'use strict';

  2. const Matrix = require('ml-matrix');
  3. const EVD = Matrix.DC.EVD;
  4. const SVD = Matrix.DC.SVD;
  5. const Stat = require('ml-stat').matrix;
  6. const mean = Stat.mean;
  7. const stdev = Stat.standardDeviation;

  8. const defaultOptions = {
  9.     isCovarianceMatrix: false,
  10.     center: true,
  11.     scale: false
  12. };

  13. /**
  14. * Creates new PCA (Principal Component Analysis) from the dataset
  15. * @param {Matrix} dataset - dataset or covariance matrix
  16. * @param {Object} options
  17. * @param {boolean} [options.isCovarianceMatrix=false] - true if the dataset is a covariance matrix
  18. * @param {boolean} [options.center=true] - should the data be centered (subtract the mean)
  19. * @param {boolean} [options.scale=false] - should the data be scaled (divide by the standard deviation)
  20. * */
  21. class PCA {
  22.     constructor(dataset, options) {
  23.         if (dataset === true) {
  24.             const model = options;
  25.             this.center = model.center;
  26.             this.scale = model.scale;
  27.             this.means = model.means;
  28.             this.stdevs = model.stdevs;
  29.             this.U = Matrix.checkMatrix(model.U);
  30.             this.S = model.S;
  31.             return;
  32.         }

  33.         options = Object.assign({}, defaultOptions, options);

  34.         this.center = false;
  35.         this.scale = false;
  36.         this.means = null;
  37.         this.stdevs = null;

  38.         if (options.isCovarianceMatrix) { // user provided a covariance matrix instead of dataset
  39.             this._computeFromCovarianceMatrix(dataset);
  40.             return;
  41.         }

  42.         var useCovarianceMatrix;
  43.         if (typeof options.useCovarianceMatrix === 'boolean') {
  44.             useCovarianceMatrix = options.useCovarianceMatrix;
  45.         } else {
  46.             useCovarianceMatrix = dataset.length > dataset[0].length;
  47.         }

  48.         if (useCovarianceMatrix) { // user provided a dataset but wants us to compute and use the covariance matrix
  49.             dataset = this._adjust(dataset, options);
  50.             const covarianceMatrix = dataset.transposeView().mmul(dataset).div(dataset.rows - 1);
  51.             this._computeFromCovarianceMatrix(covarianceMatrix);
  52.         } else {
  53.             dataset = this._adjust(dataset, options);
  54.             var svd = new SVD(dataset, {
  55.                 computeLeftSingularVectors: false,
  56.                 computeRightSingularVectors: true,
  57.                 autoTranspose: true
  58.             });

  59.             this.U = svd.rightSingularVectors;

  60.             const singularValues = svd.diagonal;
  61.             const eigenvalues = new Array(singularValues.length);
  62.             for (var i = 0; i < singularValues.length; i++) {
  63.                 eigenvalues[i] = singularValues[i] * singularValues[i] / (dataset.length - 1);
  64.             }
  65.             this.S = eigenvalues;
  66.         }
  67.     }

  68.     /**
  69.      * Load a PCA model from JSON
  70.      * @param {Object} model
  71.      * @return {PCA}
  72.      */
  73.     static load(model) {
  74.         if (model.name !== 'PCA')
  75.             throw new RangeError('Invalid model: ' + model.name);
  76.         return new PCA(true, model);
  77.     }

  78.     /**
  79.      * Project the dataset into the PCA space
  80.      * @param {Matrix} dataset
  81.      * @return {Matrix} dataset projected in the PCA space
  82.      */
  83.     predict(dataset) {
  84.         dataset = new Matrix(dataset);

  85.         if (this.center) {
  86.             dataset.subRowVector(this.means);
  87.             if (this.scale) {
  88.                 dataset.divRowVector(this.stdevs);
  89.             }
  90.         }

  91.         return dataset.mmul(this.U);
  92.     }

  93.     /**
  94.      * Returns the proportion of variance for each component
  95.      * @return {[number]}
  96.      */
  97.     getExplainedVariance() {
  98.         var sum = 0;
  99.         for (var i = 0; i < this.S.length; i++) {
  100.             sum += this.S[i];
  101.         }
  102.         return this.S.map(value => value / sum);
  103.     }

  104.     /**
  105.      * Returns the cumulative proportion of variance
  106.      * @return {[number]}
  107.      */
  108.     getCumulativeVariance() {
  109.         var explained = this.getExplainedVariance();
  110.         for (var i = 1; i < explained.length; i++) {
  111.             explained[i] += explained[i - 1];
  112.         }
  113.         return explained;
  114.     }

  115.     /**
  116.      * Returns the Eigenvectors of the covariance matrix
  117.      * @returns {Matrix}
  118.      */
  119.     getEigenvectors() {
  120.         return this.U;
  121.     }

  122.     /**
  123.      * Returns the Eigenvalues (on the diagonal)
  124.      * @returns {[number]}
  125.      */
  126.     getEigenvalues() {
  127.         return this.S;
  128.     }

  129.     /**
  130.      * Returns the standard deviations of the principal components
  131.      * @returns {[number]}
  132.      */
  133.     getStandardDeviations() {
  134.         return this.S.map(x => Math.sqrt(x));
  135.     }

  136.     /**
  137.      * Returns the loadings matrix
  138.      * @return {Matrix}
  139.      */
  140.     getLoadings() {
  141.         return this.U.transpose();
  142.     }

  143.     /**
  144.      * Export the current model to a JSON object
  145.      * @return {Object} model
  146.      */
  147.     toJSON() {
  148.         return {
  149.             name: 'PCA',
  150.             center: this.center,
  151.             scale: this.scale,
  152.             means: this.means,
  153.             stdevs: this.stdevs,
  154.             U: this.U,
  155.             S: this.S,
  156.         };
  157.     }

  158.     _adjust(dataset, options) {
  159.         this.center = !!options.center;
  160.         this.scale = !!options.scale;

  161.         dataset = new Matrix(dataset);

  162.         if (this.center) {
  163.             const means = mean(dataset);
  164.             const stdevs = this.scale ? stdev(dataset, means, true) : null;
  165.             this.means = means;
  166.             dataset.subRowVector(means);
  167.             if (this.scale) {
  168.                 for (var i = 0; i < stdevs.length; i++) {
  169.                     if (stdevs[i] === 0) {
  170.                         throw new RangeError('Cannot scale the dataset (standard deviation is zero at index ' + i);
  171.                     }
  172.                 }
  173.                 this.stdevs = stdevs;
  174.                 dataset.divRowVector(stdevs);
  175.             }
  176.         }

  177.         return dataset;
  178.     }

  179.     _computeFromCovarianceMatrix(dataset) {
  180.         const evd = new EVD(dataset, {assumeSymmetric: true});
  181.         this.U = evd.eigenvectorMatrix;
  182.         for (var i = 0; i < this.U.length; i++) {
  183.             this.U[i].reverse();
  184.         }
  185.         this.S = evd.realEigenvalues.reverse();
  186.     }
  187. }

  188. module.exports = PCA;
复制代码

您需要登录后才可以回帖 登录 | 我要注册

本版微信群
加好友,备注jltj
拉您入交流群
GMT+8, 2026-1-23 02:38