svd.ts
Version:
A lightweight, isomorphic TypeScript implementation for computing Singular Value Decomposition (SVD) of matrix in Node.js and browsers.
56 lines (55 loc) • 1.52 kB
JavaScript
;
/* for SVD decomposition */
Object.defineProperty(exports, "__esModule", { value: true });
exports.transpose = transpose;
exports.matVecMul = matVecMul;
exports.dot = dot;
exports.norm = norm;
exports.normalize = normalize;
exports.subtract = subtract;
exports.outer = outer;
exports.matSub = matSub;
exports.diag = diag;
exports.matMul = matMul;
function transpose(A) {
return A[0].map((_, i) => A.map(row => row[i]));
}
function matVecMul(A, x) {
return A.map(row => row.reduce((acc, v, i) => acc + v * x[i], 0));
}
function dot(a, b) {
return a.reduce((sum, ai, i) => sum + ai * b[i], 0);
}
function norm(x) {
return Math.sqrt(dot(x, x));
}
function normalize(x) {
const n = norm(x);
if (n < 1e-12)
return Array(x.length).fill(0);
return x.map(v => v / n);
}
function subtract(a, b) {
return a.map((v, i) => v - b[i]);
}
function outer(a, b) {
return a.map(ai => b.map(bj => ai * bj));
}
function matSub(A, B) {
return A.map((row, i) => row.map((v, j) => v - B[i][j]));
}
/* for reconstruction */
function diag(s) {
// Create a diagonal matrix from a vector
return s.map((v, i) => s.map((_, j) => (i === j ? v : 0)));
}
function matMul(A, B) {
const result = Array(A.length)
.fill(0)
.map(() => Array(B[0].length).fill(0));
for (let i = 0; i < A.length; ++i)
for (let j = 0; j < B[0].length; ++j)
for (let k = 0; k < B.length; ++k)
result[i][j] += A[i][k] * B[k][j];
return result;
}