@danielsimonjr/mathts-matrix 0.1.1 → 0.1.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -192,167 +192,165 @@ declare abstract class Matrix<T = number> {
192
192
  declare function isMatrix<T = number>(value: unknown): value is Matrix<T>;
193
193
 
194
194
  /**
195
- * Sparse Matrix Implementation (CSR Format)
196
- *
197
- * Compressed Sparse Row (CSR) format sparse matrix for efficient storage
198
- * and operations on matrices with many zero elements.
195
+ * Dense Matrix Implementation
199
196
  *
200
- * CSR stores:
201
- * - values: Non-zero values in row-major order
202
- * - colIndices: Column index for each non-zero value
203
- * - rowPointers: Index into values/colIndices where each row starts
197
+ * Row-major dense matrix backed by Float64Array for efficient storage
198
+ * and operations. Supports views (slices without copying) where possible.
204
199
  *
205
200
  * @packageDocumentation
206
201
  */
207
202
 
208
203
  /**
209
- * Sparse matrix using Compressed Sparse Row (CSR) format
204
+ * Dense matrix implementation using Float64Array
210
205
  *
211
- * Efficient for:
212
- * - Row slicing and iteration
213
- * - Sparse matrix-vector multiplication
214
- * - Matrices with many zeros (typically < 10% non-zero)
206
+ * Data is stored in row-major order for cache-friendly row access.
207
+ * All operations return new matrices (immutable API).
215
208
  */
216
- declare class SparseMatrix extends Matrix<number> {
217
- readonly type: "SparseMatrix";
209
+ declare class DenseMatrix extends Matrix<number> {
210
+ readonly type: "DenseMatrix";
218
211
  readonly rows: number;
219
212
  readonly cols: number;
220
213
  /**
221
- * Non-zero values in row-major order
214
+ * Internal data storage (row-major Float64Array)
222
215
  */
223
- private readonly _data;
216
+ private readonly data;
224
217
  /**
225
- * Column indices for each non-zero value
218
+ * Whether this matrix is a view into another matrix's data
226
219
  */
227
- private readonly _colIndices;
220
+ private readonly isView;
228
221
  /**
229
- * Row pointers: rowPointers[i] = index of first non-zero in row i
230
- * rowPointers[rows] = total number of non-zeros (nnz)
222
+ * Offset into data array (for views)
231
223
  */
232
- private readonly _rowPointers;
224
+ private readonly offset;
233
225
  /**
234
- * Create a sparse matrix from CSR components
226
+ * Stride between rows (for views)
227
+ */
228
+ private readonly rowStride;
229
+ /**
230
+ * Create a new DenseMatrix
235
231
  *
236
232
  * @param rows - Number of rows
237
233
  * @param cols - Number of columns
238
- * @param values - Non-zero values
239
- * @param colIndices - Column index for each value
240
- * @param rowPointers - Row start indices
234
+ * @param data - Optional initial data (row-major order)
241
235
  */
242
- constructor(rows: number, cols: number, values: Float64Array | number[], colIndices: Int32Array | number[], rowPointers: Int32Array | number[]);
236
+ constructor(rows: number, cols: number, data?: Float64Array | number[] | number[][], viewConfig?: {
237
+ isView: boolean;
238
+ offset: number;
239
+ rowStride: number;
240
+ });
243
241
  /**
244
- * Create a sparse matrix from a dense matrix
245
- *
246
- * @param dense - Dense matrix to convert
247
- * @param dropTolerance - Values below this threshold are treated as zero
242
+ * Create a matrix from a nested array
248
243
  */
249
- static fromDense(dense: DenseMatrix, dropTolerance?: number): SparseMatrix;
244
+ static fromArray(arr: number[][]): DenseMatrix;
250
245
  /**
251
- * Create a sparse matrix from coordinate (COO) format
252
- *
253
- * @param rows - Number of rows
254
- * @param cols - Number of columns
255
- * @param entries - Array of {row, col, value} entries
246
+ * Create a matrix from a flat array with specified dimensions
256
247
  */
257
- static fromCOO(rows: number, cols: number, entries: Array<{
258
- row: number;
259
- col: number;
260
- value: number;
261
- }>): SparseMatrix;
248
+ static fromFlat(rows: number, cols: number, data: number[]): DenseMatrix;
262
249
  /**
263
- * Create a zero sparse matrix
250
+ * Create a zero matrix
264
251
  */
265
- static zeros(rows: number, cols: number): SparseMatrix;
252
+ static zeros(rows: number, cols: number): DenseMatrix;
266
253
  /**
267
- * Create a sparse identity matrix
254
+ * Create a matrix filled with ones
268
255
  */
269
- static identity(n: number): SparseMatrix;
256
+ static ones(rows: number, cols: number): DenseMatrix;
270
257
  /**
271
- * Create a sparse diagonal matrix
258
+ * Create an identity matrix
272
259
  */
273
- static diag(values: number[]): SparseMatrix;
260
+ static identity(n: number): DenseMatrix;
274
261
  /**
275
- * Number of non-zero elements
262
+ * Create a diagonal matrix from values
276
263
  */
277
- get nnz(): number;
264
+ static diag(values: number[]): DenseMatrix;
278
265
  /**
279
- * Sparsity: fraction of zero elements
266
+ * Create a matrix filled with a constant value
280
267
  */
281
- get sparsity(): number;
268
+ static fill(rows: number, cols: number, value: number): DenseMatrix;
282
269
  /**
283
- * Density: fraction of non-zero elements
270
+ * Create a matrix with random values in [0, 1)
284
271
  */
285
- get density(): number;
272
+ static random(rows: number, cols: number): DenseMatrix;
286
273
  /**
287
- * Get element at (row, col) - O(log(nnz_in_row)) for sorted columns
274
+ * Get element at (row, col)
275
+ * O(1) access time
288
276
  */
289
277
  get(row: number, col: number): number;
290
278
  /**
291
- * Set element at (row, col) - returns new matrix (immutable)
279
+ * Set element at (row, col) - returns new matrix
292
280
  */
293
- set(row: number, col: number, value: number): SparseMatrix;
281
+ set(row: number, col: number, value: number): DenseMatrix;
294
282
  /**
295
- * Get a row as a sparse 1×n matrix
283
+ * Get the raw Float64Array data (copy if view, reference otherwise)
296
284
  */
297
- row(index: number): SparseMatrix;
285
+ private toFlatFloat64Array;
298
286
  /**
299
- * Get a column as a sparse m×1 matrix
287
+ * Get a row as a 1×n matrix (view, no copy)
300
288
  */
301
- column(index: number): SparseMatrix;
289
+ row(index: number): DenseMatrix;
290
+ /**
291
+ * Get a column as an m×1 matrix (copy, since data is row-major)
292
+ */
293
+ column(index: number): DenseMatrix;
302
294
  /**
303
295
  * Get a submatrix
304
296
  */
305
- slice(spec: SliceSpec): SparseMatrix;
297
+ slice(spec: SliceSpec): DenseMatrix;
306
298
  /**
307
299
  * Get the diagonal elements
308
300
  */
309
- diagonal(k?: number): SparseMatrix;
301
+ diagonal(k?: number): DenseMatrix;
310
302
  /**
311
- * Sparse matrix addition
303
+ * Matrix addition
312
304
  */
313
- add(other: Matrix<number>): SparseMatrix;
314
- private addSparse;
305
+ add(other: Matrix<number>): DenseMatrix;
315
306
  /**
316
- * Sparse matrix subtraction
307
+ * Matrix subtraction
317
308
  */
318
- subtract(other: Matrix<number>): SparseMatrix;
309
+ subtract(other: Matrix<number>): DenseMatrix;
319
310
  /**
320
311
  * Element-wise multiplication (Hadamard product)
321
312
  */
322
- multiplyElementwise(other: Matrix<number>): SparseMatrix;
313
+ multiplyElementwise(other: Matrix<number>): DenseMatrix;
323
314
  /**
324
- * Sparse matrix multiplication
315
+ * Matrix multiplication
325
316
  */
326
- multiply(other: Matrix<number>): SparseMatrix;
327
- private multiplySparse;
317
+ multiply(other: Matrix<number>): DenseMatrix;
328
318
  /**
329
319
  * Scalar multiplication
330
320
  */
331
- scale(scalar: number): SparseMatrix;
321
+ scale(scalar: number): DenseMatrix;
332
322
  /**
333
- * Sparse matrix transpose
323
+ * Matrix transpose
334
324
  */
335
- transpose(): SparseMatrix;
325
+ transpose(): DenseMatrix;
336
326
  /**
337
327
  * Negate all elements
338
328
  */
339
- negate(): SparseMatrix;
329
+ negate(): DenseMatrix;
340
330
  /**
341
331
  * Sum of all elements
342
332
  */
343
333
  sum(): number;
344
334
  /**
345
- * Frobenius norm
335
+ * Mean of all elements
336
+ */
337
+ mean(): number;
338
+ /**
339
+ * Minimum element
340
+ */
341
+ min(): number;
342
+ /**
343
+ * Maximum element
344
+ */
345
+ max(): number;
346
+ /**
347
+ * Frobenius norm (sqrt of sum of squared elements)
346
348
  */
347
349
  norm(): number;
348
350
  /**
349
351
  * Trace (sum of diagonal elements)
350
352
  */
351
353
  trace(): number;
352
- /**
353
- * Convert to dense matrix
354
- */
355
- toDense(): DenseMatrix;
356
354
  /**
357
355
  * Convert to nested array
358
356
  */
@@ -361,209 +359,213 @@ declare class SparseMatrix extends Matrix<number> {
361
359
  * Convert to flat array (row-major)
362
360
  */
363
361
  toFlatArray(): number[];
362
+ /**
363
+ * Get the underlying Float64Array (copy)
364
+ */
365
+ toFloat64Array(): Float64Array;
364
366
  /**
365
367
  * Clone the matrix
366
368
  */
367
- clone(): SparseMatrix;
369
+ clone(): DenseMatrix;
368
370
  /**
369
- * Get the CSR components
371
+ * Convert to sparse matrix (CSR format)
372
+ *
373
+ * This is a synchronous conversion that creates a SparseMatrix
374
+ * containing only the non-zero elements of this matrix.
375
+ *
376
+ * @param dropTolerance - Values below this threshold are treated as zero
377
+ * @returns SparseMatrix representation (typed as the `Matrix` base — the
378
+ * `SparseMatrix` subtype is loaded lazily to avoid an import cycle)
370
379
  */
371
- getCSR(): {
372
- values: Float64Array;
373
- colIndices: Int32Array;
374
- rowPointers: Int32Array;
375
- };
380
+ toSparse(dropTolerance?: number): Matrix;
376
381
  /**
377
- * Iterate over non-zero entries
382
+ * Iterate over entries with indices
378
383
  */
379
384
  entries(): IterableIterator<MatrixEntry<number>>;
380
385
  /**
381
- * Iterate over non-zero values
386
+ * Iterate over values (row-major)
382
387
  */
383
388
  values(): IterableIterator<number>;
384
389
  /**
385
- * Iterate over all values (including zeros, row-major)
386
- */
387
- allValues(): IterableIterator<number>;
388
- /**
389
- * Support for...of iteration (iterates over non-zero values)
390
+ * Support for...of iteration (iterates over values)
390
391
  */
391
392
  [Symbol.iterator](): IterableIterator<number>;
392
393
  /**
393
- * Apply a function to each non-zero element
394
+ * Apply a function to each element
394
395
  */
395
- mapNonZeros(fn: (value: number, row: number, col: number) => number): SparseMatrix;
396
+ map(fn: (value: number, row: number, col: number) => number): DenseMatrix;
396
397
  /**
397
- * Apply a function to each element (including zeros)
398
- * Warning: This may create a dense result
398
+ * Apply a function to each element (no return, for side effects)
399
399
  */
400
- map(fn: (value: number, row: number, col: number) => number): SparseMatrix;
400
+ forEach(fn: (value: number, row: number, col: number) => void): void;
401
401
  }
402
402
  /**
403
- * Type guard for SparseMatrix
403
+ * Type guard for DenseMatrix
404
404
  */
405
- declare function isSparseMatrix(value: unknown): value is SparseMatrix;
405
+ declare function isDenseMatrix(value: unknown): value is DenseMatrix;
406
406
 
407
407
  /**
408
- * Dense Matrix Implementation
408
+ * Sparse Matrix Implementation (CSR Format)
409
409
  *
410
- * Row-major dense matrix backed by Float64Array for efficient storage
411
- * and operations. Supports views (slices without copying) where possible.
410
+ * Compressed Sparse Row (CSR) format sparse matrix for efficient storage
411
+ * and operations on matrices with many zero elements.
412
+ *
413
+ * CSR stores:
414
+ * - values: Non-zero values in row-major order
415
+ * - colIndices: Column index for each non-zero value
416
+ * - rowPointers: Index into values/colIndices where each row starts
412
417
  *
413
418
  * @packageDocumentation
414
419
  */
415
420
 
416
421
  /**
417
- * Dense matrix implementation using Float64Array
422
+ * Sparse matrix using Compressed Sparse Row (CSR) format
418
423
  *
419
- * Data is stored in row-major order for cache-friendly row access.
420
- * All operations return new matrices (immutable API).
424
+ * Efficient for:
425
+ * - Row slicing and iteration
426
+ * - Sparse matrix-vector multiplication
427
+ * - Matrices with many zeros (typically < 10% non-zero)
421
428
  */
422
- declare class DenseMatrix extends Matrix<number> {
423
- readonly type: "DenseMatrix";
429
+ declare class SparseMatrix extends Matrix<number> {
430
+ readonly type: "SparseMatrix";
424
431
  readonly rows: number;
425
432
  readonly cols: number;
426
433
  /**
427
- * Internal data storage (row-major Float64Array)
428
- */
429
- private readonly data;
430
- /**
431
- * Whether this matrix is a view into another matrix's data
434
+ * Non-zero values in row-major order
432
435
  */
433
- private readonly isView;
436
+ private readonly _data;
434
437
  /**
435
- * Offset into data array (for views)
438
+ * Column indices for each non-zero value
436
439
  */
437
- private readonly offset;
440
+ private readonly _colIndices;
438
441
  /**
439
- * Stride between rows (for views)
442
+ * Row pointers: rowPointers[i] = index of first non-zero in row i
443
+ * rowPointers[rows] = total number of non-zeros (nnz)
440
444
  */
441
- private readonly rowStride;
445
+ private readonly _rowPointers;
442
446
  /**
443
- * Create a new DenseMatrix
447
+ * Create a sparse matrix from CSR components
444
448
  *
445
449
  * @param rows - Number of rows
446
450
  * @param cols - Number of columns
447
- * @param data - Optional initial data (row-major order)
451
+ * @param values - Non-zero values
452
+ * @param colIndices - Column index for each value
453
+ * @param rowPointers - Row start indices
448
454
  */
449
- constructor(rows: number, cols: number, data?: Float64Array | number[] | number[][], viewConfig?: {
450
- isView: boolean;
451
- offset: number;
452
- rowStride: number;
453
- });
455
+ constructor(rows: number, cols: number, values: Float64Array | number[], colIndices: Int32Array | number[], rowPointers: Int32Array | number[]);
454
456
  /**
455
- * Create a matrix from a nested array
457
+ * Create a sparse matrix from a dense matrix
458
+ *
459
+ * @param dense - Dense matrix to convert
460
+ * @param dropTolerance - Values below this threshold are treated as zero
456
461
  */
457
- static fromArray(arr: number[][]): DenseMatrix;
462
+ static fromDense(dense: DenseMatrix, dropTolerance?: number): SparseMatrix;
458
463
  /**
459
- * Create a matrix from a flat array with specified dimensions
464
+ * Create a sparse matrix from coordinate (COO) format
465
+ *
466
+ * @param rows - Number of rows
467
+ * @param cols - Number of columns
468
+ * @param entries - Array of {row, col, value} entries
460
469
  */
461
- static fromFlat(rows: number, cols: number, data: number[]): DenseMatrix;
470
+ static fromCOO(rows: number, cols: number, entries: Array<{
471
+ row: number;
472
+ col: number;
473
+ value: number;
474
+ }>): SparseMatrix;
462
475
  /**
463
- * Create a zero matrix
476
+ * Create a zero sparse matrix
464
477
  */
465
- static zeros(rows: number, cols: number): DenseMatrix;
478
+ static zeros(rows: number, cols: number): SparseMatrix;
466
479
  /**
467
- * Create a matrix filled with ones
480
+ * Create a sparse identity matrix
468
481
  */
469
- static ones(rows: number, cols: number): DenseMatrix;
482
+ static identity(n: number): SparseMatrix;
470
483
  /**
471
- * Create an identity matrix
484
+ * Create a sparse diagonal matrix
472
485
  */
473
- static identity(n: number): DenseMatrix;
486
+ static diag(values: number[]): SparseMatrix;
474
487
  /**
475
- * Create a diagonal matrix from values
488
+ * Number of non-zero elements
476
489
  */
477
- static diag(values: number[]): DenseMatrix;
490
+ get nnz(): number;
478
491
  /**
479
- * Create a matrix filled with a constant value
492
+ * Sparsity: fraction of zero elements
480
493
  */
481
- static fill(rows: number, cols: number, value: number): DenseMatrix;
494
+ get sparsity(): number;
482
495
  /**
483
- * Create a matrix with random values in [0, 1)
496
+ * Density: fraction of non-zero elements
484
497
  */
485
- static random(rows: number, cols: number): DenseMatrix;
498
+ get density(): number;
486
499
  /**
487
- * Get element at (row, col)
488
- * O(1) access time
500
+ * Get element at (row, col) - O(log(nnz_in_row)) for sorted columns
489
501
  */
490
502
  get(row: number, col: number): number;
491
503
  /**
492
- * Set element at (row, col) - returns new matrix
493
- */
494
- set(row: number, col: number, value: number): DenseMatrix;
495
- /**
496
- * Get the raw Float64Array data (copy if view, reference otherwise)
504
+ * Set element at (row, col) - returns new matrix (immutable)
497
505
  */
498
- private toFlatFloat64Array;
506
+ set(row: number, col: number, value: number): SparseMatrix;
499
507
  /**
500
- * Get a row as a 1×n matrix (view, no copy)
508
+ * Get a row as a sparse 1×n matrix
501
509
  */
502
- row(index: number): DenseMatrix;
510
+ row(index: number): SparseMatrix;
503
511
  /**
504
- * Get a column as an m×1 matrix (copy, since data is row-major)
512
+ * Get a column as a sparse m×1 matrix
505
513
  */
506
- column(index: number): DenseMatrix;
514
+ column(index: number): SparseMatrix;
507
515
  /**
508
516
  * Get a submatrix
509
517
  */
510
- slice(spec: SliceSpec): DenseMatrix;
518
+ slice(spec: SliceSpec): SparseMatrix;
511
519
  /**
512
520
  * Get the diagonal elements
513
521
  */
514
- diagonal(k?: number): DenseMatrix;
522
+ diagonal(k?: number): SparseMatrix;
515
523
  /**
516
- * Matrix addition
524
+ * Sparse matrix addition
517
525
  */
518
- add(other: Matrix<number>): DenseMatrix;
526
+ add(other: Matrix<number>): SparseMatrix;
527
+ private addSparse;
519
528
  /**
520
- * Matrix subtraction
529
+ * Sparse matrix subtraction
521
530
  */
522
- subtract(other: Matrix<number>): DenseMatrix;
531
+ subtract(other: Matrix<number>): SparseMatrix;
523
532
  /**
524
533
  * Element-wise multiplication (Hadamard product)
525
534
  */
526
- multiplyElementwise(other: Matrix<number>): DenseMatrix;
535
+ multiplyElementwise(other: Matrix<number>): SparseMatrix;
527
536
  /**
528
- * Matrix multiplication
537
+ * Sparse matrix multiplication
529
538
  */
530
- multiply(other: Matrix<number>): DenseMatrix;
539
+ multiply(other: Matrix<number>): SparseMatrix;
540
+ private multiplySparse;
531
541
  /**
532
542
  * Scalar multiplication
533
543
  */
534
- scale(scalar: number): DenseMatrix;
544
+ scale(scalar: number): SparseMatrix;
535
545
  /**
536
- * Matrix transpose
546
+ * Sparse matrix transpose
537
547
  */
538
- transpose(): DenseMatrix;
548
+ transpose(): SparseMatrix;
539
549
  /**
540
550
  * Negate all elements
541
551
  */
542
- negate(): DenseMatrix;
552
+ negate(): SparseMatrix;
543
553
  /**
544
554
  * Sum of all elements
545
555
  */
546
556
  sum(): number;
547
557
  /**
548
- * Mean of all elements
549
- */
550
- mean(): number;
551
- /**
552
- * Minimum element
553
- */
554
- min(): number;
555
- /**
556
- * Maximum element
557
- */
558
- max(): number;
559
- /**
560
- * Frobenius norm (sqrt of sum of squared elements)
558
+ * Frobenius norm
561
559
  */
562
560
  norm(): number;
563
561
  /**
564
562
  * Trace (sum of diagonal elements)
565
563
  */
566
564
  trace(): number;
565
+ /**
566
+ * Convert to dense matrix
567
+ */
568
+ toDense(): DenseMatrix;
567
569
  /**
568
570
  * Convert to nested array
569
571
  */
@@ -572,49 +574,48 @@ declare class DenseMatrix extends Matrix<number> {
572
574
  * Convert to flat array (row-major)
573
575
  */
574
576
  toFlatArray(): number[];
575
- /**
576
- * Get the underlying Float64Array (copy)
577
- */
578
- toFloat64Array(): Float64Array;
579
577
  /**
580
578
  * Clone the matrix
581
579
  */
582
- clone(): DenseMatrix;
580
+ clone(): SparseMatrix;
583
581
  /**
584
- * Convert to sparse matrix (CSR format)
585
- *
586
- * This is a synchronous conversion that creates a SparseMatrix
587
- * containing only the non-zero elements of this matrix.
588
- *
589
- * @param dropTolerance - Values below this threshold are treated as zero
590
- * @returns SparseMatrix representation
582
+ * Get the CSR components
591
583
  */
592
- toSparse(dropTolerance?: number): SparseMatrix;
584
+ getCSR(): {
585
+ values: Float64Array;
586
+ colIndices: Int32Array;
587
+ rowPointers: Int32Array;
588
+ };
593
589
  /**
594
- * Iterate over entries with indices
590
+ * Iterate over non-zero entries
595
591
  */
596
592
  entries(): IterableIterator<MatrixEntry<number>>;
597
593
  /**
598
- * Iterate over values (row-major)
594
+ * Iterate over non-zero values
599
595
  */
600
596
  values(): IterableIterator<number>;
601
597
  /**
602
- * Support for...of iteration (iterates over values)
598
+ * Iterate over all values (including zeros, row-major)
599
+ */
600
+ allValues(): IterableIterator<number>;
601
+ /**
602
+ * Support for...of iteration (iterates over non-zero values)
603
603
  */
604
604
  [Symbol.iterator](): IterableIterator<number>;
605
605
  /**
606
- * Apply a function to each element
606
+ * Apply a function to each non-zero element
607
607
  */
608
- map(fn: (value: number, row: number, col: number) => number): DenseMatrix;
608
+ mapNonZeros(fn: (value: number, row: number, col: number) => number): SparseMatrix;
609
609
  /**
610
- * Apply a function to each element (no return, for side effects)
610
+ * Apply a function to each element (including zeros)
611
+ * Warning: This may create a dense result
611
612
  */
612
- forEach(fn: (value: number, row: number, col: number) => void): void;
613
+ map(fn: (value: number, row: number, col: number) => number): SparseMatrix;
613
614
  }
614
615
  /**
615
- * Type guard for DenseMatrix
616
+ * Type guard for SparseMatrix
616
617
  */
617
- declare function isDenseMatrix(value: unknown): value is DenseMatrix;
618
+ declare function isSparseMatrix(value: unknown): value is SparseMatrix;
618
619
 
619
620
  /**
620
621
  * Matrix Backend Interface
@@ -629,7 +630,7 @@ declare function isDenseMatrix(value: unknown): value is DenseMatrix;
629
630
  /**
630
631
  * Backend type identifier
631
632
  */
632
- type BackendType = 'js' | 'wasm' | 'gpu' | 'parallel';
633
+ type BackendType = 'js' | 'wasm' | 'rust-wasm' | 'gpu' | 'parallel';
633
634
  /**
634
635
  * Backend selection hints
635
636
  */
@@ -1032,10 +1033,50 @@ declare function clearFeatureCache(): void;
1032
1033
  declare function getCachedFeatures(): WasmFeatures | null;
1033
1034
 
1034
1035
  /**
1035
- * WASM Matrix Backend
1036
- *
1037
- * Implements MatrixBackend using WebAssembly for accelerated operations.
1038
- * Falls back to JSBackend when WASM is unavailable or for small matrices.
1036
+ * WASM Matrix Backend (AssemblyScript)
1037
+ *
1038
+ * Implements MatrixBackend using the AssemblyScript-compiled WebAssembly
1039
+ * module (`lib/wasm/mathts-as.wasm`, ~42 KB). Falls back to JSBackend when
1040
+ * the WASM module is unavailable or for small matrices.
1041
+ *
1042
+ * ABI:
1043
+ * The AS module exports a managed runtime (`__new` / `__pin` / `__unpin` /
1044
+ * `__collect`) and its matrix/array functions accept managed `Float64Array`
1045
+ * *header* pointers — NOT raw flat-memory pointers. A typed-array header is
1046
+ * a 12-byte block at some offset that stores (buffer, buffer, byteLength).
1047
+ *
1048
+ * To call e.g. `matrix_add(a, b, result)` from JS, we have to:
1049
+ * 1. `__new(byteLength, 1)` — allocate the data buffer (id=1 = ArrayBuffer)
1050
+ * 2. `__pin(buffer)` — pin so it survives GC while building header
1051
+ * 3. `__new(12, 5)` — allocate the Float64Array header (id=5)
1052
+ * 4. Write [buffer, buffer, byteLength] into the header
1053
+ * 5. Copy caller data into the buffer
1054
+ * 6. `__unpin(buffer)` — the header now owns the buffer reference
1055
+ *
1056
+ * The Rust artifact has no managed runtime and uses a completely different
1057
+ * ABI (camelCase exports, flat-memory raw pointers); for that backend, use
1058
+ * `RustWASMBackend` (from `./RustWASMBackend.ts`).
1059
+ *
1060
+ * Naming map (Rust ↔ AssemblyScript) — for cross-backend reference:
1061
+ *
1062
+ * Op Rust (camelCase, flat ptrs) AS (snake_case, header refs)
1063
+ * ------------------ --------------------------------- -------------------------------
1064
+ * add add(aPtr,bPtr,n,resPtr) matrix_add(a,b,result)
1065
+ * subtract subtract(aPtr,bPtr,n,resPtr) matrix_sub(a,b,result)
1066
+ * multiplyElementwise simdMulF64(aPtr,bPtr,resPtr,n) matrix_mul_elementwise(a,b,result)
1067
+ * divideElementwise (none) matrix_div_elementwise(a,b,result)
1068
+ * scale simdScaleF64(aPtr,s,resPtr,n) matrix_scale(a,scalar,result)
1069
+ * abs simdAbsF64(aPtr,resPtr,n) array_abs(a,result)
1070
+ * negate simdScaleF64(aPtr,-1,resPtr,n) matrix_neg(a,result)
1071
+ * multiply multiplyDense(a,r,c,b,r,c,res) matrix_multiply(a,aRows,aCols,b,bCols,result)
1072
+ * transpose transpose(a,r,c,res) matrix_transpose(a,rows,cols,result)
1073
+ * sum simdSumF64(aPtr,n) array_sum(a)
1074
+ * norm simdNormF64(aPtr,n) array_norm(a)
1075
+ * dot dotProduct(aPtr,bPtr,n) array_dot(a,b)
1076
+ *
1077
+ * AssemblyScript has no LU / QR / Cholesky / inverse / determinant exports,
1078
+ * so those operations fall back to the JS implementation. The Rust backend
1079
+ * has them — route those calls through `RustWASMBackend` if you need WASM.
1039
1080
  *
1040
1081
  * @packageDocumentation
1041
1082
  */
@@ -1046,16 +1087,18 @@ declare function getCachedFeatures(): WasmFeatures | null;
1046
1087
  interface WASMBackendConfig {
1047
1088
  /** Minimum elements to use WASM (default: 100) */
1048
1089
  minElements?: number;
1049
- /** Path to WASM file */
1090
+ /** Path to WASM file (defaults to the AS artifact, `lib/wasm/mathts-as.wasm`) */
1050
1091
  wasmPath?: string;
1051
- /** Enable SIMD optimizations when available */
1092
+ /** Enable SIMD code paths if the AS module exposes them (currently a no-op
1093
+ * — AS export surface does not include `simd*` ops; kept for API stability). */
1052
1094
  useSIMD?: boolean;
1053
1095
  }
1054
1096
  /**
1055
- * WASM Backend for matrix operations
1097
+ * WASM Backend for matrix operations (AssemblyScript path).
1056
1098
  *
1057
- * Uses WebAssembly for accelerated matrix operations with SIMD support.
1058
- * Automatically falls back to JavaScript for small matrices or when WASM unavailable.
1099
+ * For the Rust path use `RustWASMBackend`. Both implement `MatrixBackend`
1100
+ * and report different `type` discriminants ('wasm' vs 'rust-wasm') so that
1101
+ * `BackendManager` can route operations to the correct one.
1059
1102
  */
1060
1103
  declare class WASMBackend implements MatrixBackend {
1061
1104
  readonly type: BackendType;
@@ -1063,23 +1106,27 @@ declare class WASMBackend implements MatrixBackend {
1063
1106
  private wasmModule;
1064
1107
  private features;
1065
1108
  private initPromise;
1109
+ /** Pooled allocations — see `AsAllocCache` for rationale. */
1110
+ private allocCache;
1066
1111
  constructor(config?: WASMBackendConfig);
1067
- /**
1068
- * Check if WASM is available in the current environment
1069
- */
1070
1112
  isAvailable(): boolean;
1071
- /**
1072
- * Initialize the WASM backend
1073
- */
1074
1113
  initialize(): Promise<void>;
1075
1114
  private doInitialize;
1076
1115
  /**
1077
- * Check if operation should use WASM
1116
+ * Resolve the path to the AssemblyScript artifact (`lib/wasm/mathts-as.wasm`).
1117
+ *
1118
+ * On Windows, `URL.pathname` returns "/C:/foo/bar.wasm" which fs.readFile
1119
+ * interprets as drive-relative ("C:\C:\foo\..."). `fileURLToPath` does the
1120
+ * platform-correct conversion.
1078
1121
  */
1079
- private shouldUseWasm;
1122
+ private resolveAsWasmPath;
1080
1123
  /**
1081
- * Get detected WASM features
1124
+ * Compile + instantiate the AssemblyScript WASM artifact. Each
1125
+ * WASMBackend instance owns its own instance — this is intentional so
1126
+ * tests and the Rust backend can coexist in the same process.
1082
1127
  */
1128
+ private loadAsModule;
1129
+ private shouldUseWasm;
1083
1130
  getFeatures(): WasmFeatures | null;
1084
1131
  add(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
1085
1132
  subtract(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
@@ -1094,40 +1141,24 @@ declare class WASMBackend implements MatrixBackend {
1094
1141
  sumAxis(a: DenseMatrix, axis: 0 | 1): DenseMatrix;
1095
1142
  norm(a: DenseMatrix): number;
1096
1143
  dot(a: DenseMatrix, b: DenseMatrix): number;
1097
- /**
1098
- * LU Decomposition using WASM
1099
- */
1100
1144
  luDecomposition(a: DenseMatrix): Promise<{
1101
1145
  lu: DenseMatrix;
1102
1146
  perm: Int32Array;
1103
1147
  singular: boolean;
1104
1148
  }>;
1105
1149
  private luDecompositionJS;
1106
- /**
1107
- * QR Decomposition using WASM
1108
- */
1109
1150
  qrDecomposition(a: DenseMatrix): Promise<{
1110
1151
  q: DenseMatrix;
1111
1152
  r: DenseMatrix;
1112
1153
  }>;
1113
1154
  private qrDecompositionJS;
1114
- /**
1115
- * Matrix inversion using LU decomposition
1116
- */
1117
1155
  inverse(a: DenseMatrix): Promise<{
1118
1156
  inverse: DenseMatrix;
1119
1157
  singular: boolean;
1120
1158
  }>;
1121
1159
  private inverseJS;
1122
- /**
1123
- * Compute matrix determinant using LU decomposition
1124
- */
1125
1160
  determinantWasm(a: DenseMatrix): Promise<number>;
1126
1161
  private determinantJS;
1127
- /**
1128
- * Cholesky Decomposition using WASM
1129
- * For symmetric positive-definite matrices: A = L * L^T
1130
- */
1131
1162
  choleskyDecomposition(a: DenseMatrix): Promise<{
1132
1163
  l: DenseMatrix;
1133
1164
  positiveDefinite: boolean;
@@ -1143,11 +1174,11 @@ declare class WASMBackend implements MatrixBackend {
1143
1174
  getConfig(): Required<WASMBackendConfig>;
1144
1175
  }
1145
1176
  /**
1146
- * Global WASM backend instance
1177
+ * Global WASM backend instance (AssemblyScript path)
1147
1178
  */
1148
1179
  declare const wasmBackend: WASMBackend;
1149
1180
  /**
1150
- * Create a WASM backend with custom configuration
1181
+ * Create a WASM backend (AssemblyScript path) with custom configuration
1151
1182
  */
1152
1183
  declare function createWASMBackend(config?: WASMBackendConfig): WASMBackend;
1153
1184
 
@@ -1893,170 +1924,489 @@ declare class GPUBackend {
1893
1924
  */
1894
1925
  add(a: Float32Array, b: Float32Array, rows: number, cols: number): Promise<Float32Array>;
1895
1926
  /**
1896
- * Multiply two matrices
1927
+ * Multiply two matrices
1928
+ */
1929
+ matmul(a: Float32Array, b: Float32Array, M: number, K: number, N: number): Promise<Float32Array>;
1930
+ /**
1931
+ * Transpose a matrix
1932
+ */
1933
+ transpose(a: Float32Array, rows: number, cols: number): Promise<Float32Array>;
1934
+ /**
1935
+ * Scale a matrix by a scalar
1936
+ */
1937
+ scale(a: Float32Array, scalar: number): Promise<Float32Array>;
1938
+ /**
1939
+ * Get backend statistics
1940
+ */
1941
+ getStats(): {
1942
+ status: GPUBackendStatus;
1943
+ capabilities: GPUCapabilities | null;
1944
+ bufferPool: {
1945
+ totalBuffers: number;
1946
+ inUseBuffers: number;
1947
+ cachedBuffers: number;
1948
+ } | null;
1949
+ shaders: {
1950
+ cachedShaders: number;
1951
+ cachedPipelines: number;
1952
+ } | null;
1953
+ };
1954
+ /**
1955
+ * Destroy the backend
1956
+ */
1957
+ destroy(): void;
1958
+ }
1959
+ /**
1960
+ * Get the global GPU backend
1961
+ */
1962
+ declare function getGlobalGPUBackend(): GPUBackend;
1963
+ /**
1964
+ * Initialize the global GPU backend
1965
+ */
1966
+ declare function initializeGlobalGPUBackend(options?: GPUBackendOptions): Promise<boolean>;
1967
+ /**
1968
+ * Destroy the global GPU backend
1969
+ */
1970
+ declare function destroyGlobalGPUBackend(): void;
1971
+
1972
+ /**
1973
+ * GPU Matrix Backend Adapter
1974
+ *
1975
+ * Adapts GPUBackend to implement the MatrixBackend interface,
1976
+ * enabling seamless integration with the backend selection system.
1977
+ *
1978
+ * @packageDocumentation
1979
+ */
1980
+
1981
+ /**
1982
+ * Configuration for GPU Matrix Backend
1983
+ */
1984
+ interface GPUMatrixBackendConfig {
1985
+ /** Minimum elements to use GPU (default: 65536 = 256x256) */
1986
+ minElements?: number;
1987
+ /** Use global GPU backend instance */
1988
+ useGlobalBackend?: boolean;
1989
+ /** GPU backend options */
1990
+ gpuOptions?: GPUBackendOptions;
1991
+ /** Fall back to JS on GPU errors */
1992
+ fallbackOnError?: boolean;
1993
+ }
1994
+ /**
1995
+ * GPU Matrix Backend
1996
+ *
1997
+ * Implements MatrixBackend interface using WebGPU compute shaders.
1998
+ * Provides significant acceleration for large matrices.
1999
+ *
2000
+ * @example
2001
+ * ```typescript
2002
+ * const gpu = new GPUMatrixBackend();
2003
+ * await gpu.initialize();
2004
+ *
2005
+ * const result = gpu.multiply(matrixA, matrixB);
2006
+ * ```
2007
+ */
2008
+ declare class GPUMatrixBackend implements MatrixBackend {
2009
+ readonly type: BackendType;
2010
+ private config;
2011
+ private backend;
2012
+ private capabilities;
2013
+ private initPromise;
2014
+ private _available;
2015
+ constructor(config?: GPUMatrixBackendConfig);
2016
+ /**
2017
+ * Check if GPU is available in the current environment
2018
+ */
2019
+ isAvailable(): boolean;
2020
+ /**
2021
+ * Initialize the GPU backend
2022
+ */
2023
+ initialize(): Promise<void>;
2024
+ private doInitialize;
2025
+ /**
2026
+ * Check if operation should use GPU
2027
+ */
2028
+ private shouldUseGPU;
2029
+ /**
2030
+ * Execute GPU operation with fallback
2031
+ */
2032
+ private executeWithFallback;
2033
+ /**
2034
+ * Get GPU capabilities
2035
+ */
2036
+ getCapabilities(): GPUCapabilities | null;
2037
+ /**
2038
+ * Get backend statistics
2039
+ */
2040
+ getStats(): ReturnType<GPUBackend['getStats']> | null;
2041
+ add(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2042
+ /**
2043
+ * Async add operation using GPU
2044
+ */
2045
+ addAsync(a: DenseMatrix, b: DenseMatrix): Promise<DenseMatrix>;
2046
+ subtract(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2047
+ multiplyElementwise(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2048
+ divideElementwise(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2049
+ scale(a: DenseMatrix, scalar: number): DenseMatrix;
2050
+ /**
2051
+ * Async scale operation using GPU
2052
+ */
2053
+ scaleAsync(a: DenseMatrix, scalar: number): Promise<DenseMatrix>;
2054
+ abs(a: DenseMatrix): DenseMatrix;
2055
+ negate(a: DenseMatrix): DenseMatrix;
2056
+ multiply(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2057
+ /**
2058
+ * Async matrix multiplication using GPU
2059
+ */
2060
+ multiplyAsync(a: DenseMatrix, b: DenseMatrix): Promise<DenseMatrix>;
2061
+ transpose(a: DenseMatrix): DenseMatrix;
2062
+ /**
2063
+ * Async transpose using GPU
2064
+ */
2065
+ transposeAsync(a: DenseMatrix): Promise<DenseMatrix>;
2066
+ sum(a: DenseMatrix): number;
2067
+ sumAxis(a: DenseMatrix, axis: 0 | 1): DenseMatrix;
2068
+ norm(a: DenseMatrix): number;
2069
+ dot(a: DenseMatrix, b: DenseMatrix): number;
2070
+ /**
2071
+ * Update configuration
2072
+ */
2073
+ updateConfig(config: Partial<GPUMatrixBackendConfig>): void;
2074
+ /**
2075
+ * Get current configuration
2076
+ */
2077
+ getConfig(): Required<GPUMatrixBackendConfig>;
2078
+ /**
2079
+ * Destroy the backend
2080
+ */
2081
+ destroy(): void;
2082
+ }
2083
+ /**
2084
+ * Global GPU matrix backend instance
2085
+ */
2086
+ declare const gpuMatrixBackend: GPUMatrixBackend;
2087
+ /**
2088
+ * Create a GPU matrix backend with custom configuration
2089
+ */
2090
+ declare function createGPUMatrixBackend(config?: GPUMatrixBackendConfig): GPUMatrixBackend;
2091
+
2092
+ /**
2093
+ * Rust WASM Matrix Backend
2094
+ *
2095
+ * Implements MatrixBackend using the Rust-compiled WebAssembly module (648 KB).
2096
+ * Designed for heavy operations: large matrix multiply (faer), FFT (rustfft),
2097
+ * eigendecomposition, sparse algebra, and SIMD-accelerated array operations.
2098
+ *
2099
+ * This backend sits alongside the existing WASMBackend (AssemblyScript) and
2100
+ * is selected by BackendManager for large matrices and heavy operations.
2101
+ *
2102
+ * Memory model:
2103
+ * Uses a bump allocator on the JS side to write data into WASM linear
2104
+ * memory. The allocator is reset between operations (batch-free pattern).
2105
+ * This avoids the overhead of per-allocation malloc/free calls.
2106
+ *
2107
+ * @packageDocumentation
2108
+ */
2109
+
2110
+ /**
2111
+ * Rust WASM Backend configuration
2112
+ */
2113
+ interface RustWASMBackendConfig {
2114
+ /** Minimum elements to use Rust WASM (default: 1000) */
2115
+ minElements?: number;
2116
+ /** Path to the Rust WASM binary */
2117
+ wasmPath?: string;
2118
+ }
2119
+ /**
2120
+ * Rust WASM Backend for matrix operations.
2121
+ *
2122
+ * Uses the Rust WASM module for heavy computation, with automatic
2123
+ * fallback to JSBackend when the module is unavailable or for small matrices.
2124
+ *
2125
+ * The backend registers as type 'wasm' so it can serve as a drop-in
2126
+ * replacement or complement to the AssemblyScript WASMBackend. When both
2127
+ * are needed, use BackendManager's operation-specific routing.
2128
+ */
2129
+ declare class RustWASMBackend implements MatrixBackend {
2130
+ /**
2131
+ * Backend type identifier.
2132
+ * Uses 'rust-wasm' to distinguish from the AssemblyScript WASMBackend.
2133
+ */
2134
+ readonly type: BackendType;
2135
+ private config;
2136
+ private exports;
2137
+ private initPromise;
2138
+ constructor(config?: RustWASMBackendConfig);
2139
+ /**
2140
+ * Check if WebAssembly is available in the current environment.
2141
+ */
2142
+ isAvailable(): boolean;
2143
+ /**
2144
+ * Initialize the Rust WASM backend.
2145
+ * Loads the WASM binary and caches the exports.
2146
+ */
2147
+ initialize(): Promise<void>;
2148
+ private doInitialize;
2149
+ /**
2150
+ * Whether to use Rust WASM for this operation size.
2151
+ */
2152
+ private shouldUseRustWasm;
2153
+ /**
2154
+ * Whether the Rust WASM module is loaded and ready.
2155
+ */
2156
+ get isRustLoaded(): boolean;
2157
+ add(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2158
+ subtract(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2159
+ multiplyElementwise(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2160
+ divideElementwise(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2161
+ scale(a: DenseMatrix, scalar: number): DenseMatrix;
2162
+ abs(a: DenseMatrix): DenseMatrix;
2163
+ negate(a: DenseMatrix): DenseMatrix;
2164
+ multiply(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2165
+ transpose(a: DenseMatrix): DenseMatrix;
2166
+ sum(a: DenseMatrix): number;
2167
+ sumAxis(a: DenseMatrix, axis: 0 | 1): DenseMatrix;
2168
+ norm(a: DenseMatrix): number;
2169
+ dot(a: DenseMatrix, b: DenseMatrix): number;
2170
+ /**
2171
+ * LU Decomposition using Rust WASM.
2172
+ */
2173
+ luDecomposition(a: DenseMatrix): Promise<{
2174
+ lu: DenseMatrix;
2175
+ perm: Int32Array;
2176
+ singular: boolean;
2177
+ }>;
2178
+ /**
2179
+ * Eigenvalue decomposition for symmetric matrices using Rust WASM.
1897
2180
  */
1898
- matmul(a: Float32Array, b: Float32Array, M: number, K: number, N: number): Promise<Float32Array>;
2181
+ eigsSymmetric(a: DenseMatrix, precision?: number): Promise<{
2182
+ eigenvalues: Float64Array;
2183
+ eigenvectors: DenseMatrix;
2184
+ iterations: number;
2185
+ }>;
1899
2186
  /**
1900
- * Transpose a matrix
2187
+ * Matrix inversion using Rust WASM.
1901
2188
  */
1902
- transpose(a: Float32Array, rows: number, cols: number): Promise<Float32Array>;
2189
+ inverse(a: DenseMatrix): Promise<{
2190
+ inverse: DenseMatrix;
2191
+ singular: boolean;
2192
+ }>;
1903
2193
  /**
1904
- * Scale a matrix by a scalar
2194
+ * FFT using Rust WASM (rustfft).
2195
+ * Data is interleaved complex: [re0, im0, re1, im1, ...].
1905
2196
  */
1906
- scale(a: Float32Array, scalar: number): Promise<Float32Array>;
2197
+ fft(data: Float64Array, n: number, inverse?: boolean): Float64Array;
1907
2198
  /**
1908
- * Get backend statistics
2199
+ * Update configuration.
1909
2200
  */
1910
- getStats(): {
1911
- status: GPUBackendStatus;
1912
- capabilities: GPUCapabilities | null;
1913
- bufferPool: {
1914
- totalBuffers: number;
1915
- inUseBuffers: number;
1916
- cachedBuffers: number;
1917
- } | null;
1918
- shaders: {
1919
- cachedShaders: number;
1920
- cachedPipelines: number;
1921
- } | null;
1922
- };
2201
+ updateConfig(config: Partial<RustWASMBackendConfig>): void;
1923
2202
  /**
1924
- * Destroy the backend
2203
+ * Get current configuration.
1925
2204
  */
1926
- destroy(): void;
2205
+ getConfig(): Required<RustWASMBackendConfig>;
1927
2206
  }
1928
2207
  /**
1929
- * Get the global GPU backend
1930
- */
1931
- declare function getGlobalGPUBackend(): GPUBackend;
1932
- /**
1933
- * Initialize the global GPU backend
2208
+ * Global Rust WASM backend instance
1934
2209
  */
1935
- declare function initializeGlobalGPUBackend(options?: GPUBackendOptions): Promise<boolean>;
2210
+ declare const rustWasmBackend: RustWASMBackend;
1936
2211
  /**
1937
- * Destroy the global GPU backend
2212
+ * Create a Rust WASM backend with custom configuration
1938
2213
  */
1939
- declare function destroyGlobalGPUBackend(): void;
2214
+ declare function createRustWASMBackend(config?: RustWASMBackendConfig): RustWASMBackend;
1940
2215
 
1941
2216
  /**
1942
- * GPU Matrix Backend Adapter
2217
+ * Rust WASM Loader
1943
2218
  *
1944
- * Adapts GPUBackend to implement the MatrixBackend interface,
1945
- * enabling seamless integration with the backend selection system.
2219
+ * Loads and manages the Rust-compiled WebAssembly module (648 KB).
2220
+ * The Rust WASM provides heavy computation: matrix multiply (faer),
2221
+ * FFT (rustfft), eigendecomposition, sparse algebra, statistics (statrs),
2222
+ * and SIMD-accelerated array operations.
2223
+ *
2224
+ * Memory model:
2225
+ * The Rust WASM uses `#[no_mangle] extern "C"` raw exports with
2226
+ * a linear memory model. Unlike the AssemblyScript WASM, there is
2227
+ * no managed GC heap (`__new`/`__pin`/`__unpin`/`__collect`).
2228
+ * Instead, JavaScript writes data directly into WASM linear memory
2229
+ * at computed offsets and passes those offsets as pointers.
1946
2230
  *
1947
2231
  * @packageDocumentation
1948
2232
  */
1949
-
1950
2233
  /**
1951
- * Configuration for GPU Matrix Backend
2234
+ * Typed interface for Rust WASM exports.
2235
+ *
2236
+ * This is a subset of the full export surface, covering the operations
2237
+ * most useful for the matrix backend. The full module has 150+ exports
2238
+ * across algebra, arithmetic, signal, statistics, etc.
2239
+ */
2240
+ interface RustWasmExports {
2241
+ memory: WebAssembly.Memory;
2242
+ multiplyDense: (aPtr: number, aRows: number, aCols: number, bPtr: number, bRows: number, bCols: number, resultPtr: number) => void;
2243
+ multiplyDenseSIMD: (aPtr: number, aRows: number, aCols: number, bPtr: number, bRows: number, bCols: number, resultPtr: number) => void;
2244
+ multiplyVector: (aPtr: number, aRows: number, aCols: number, xPtr: number, resultPtr: number) => void;
2245
+ transpose: (dataPtr: number, rows: number, cols: number, resultPtr: number) => void;
2246
+ /** Thin SVD: writes U (m*k), S (k), V (n*k); k = min(m,n). */
2247
+ svd: (aPtr: number, m: number, n: number, uPtr: number, sPtr: number, vPtr: number, workPtr: number) => number;
2248
+ /** Singular values only: writes S (k); k = min(m,n). */
2249
+ singularValues: (aPtr: number, m: number, n: number, sPtr: number, workPtr: number) => number;
2250
+ /** Scratch length (in f64s) required by `svd`. */
2251
+ svdWorkSize: (m: number, n: number) => number;
2252
+ /** Scratch length (in f64s) required by `singularValues`. */
2253
+ singularValuesWorkSize: (m: number, n: number) => number;
2254
+ simdAddF64: (aPtr: number, bPtr: number, resultPtr: number, length: number) => void;
2255
+ simdSubF64: (aPtr: number, bPtr: number, resultPtr: number, length: number) => void;
2256
+ simdMulF64: (aPtr: number, bPtr: number, resultPtr: number, length: number) => void;
2257
+ simdScaleF64: (aPtr: number, scalar: number, resultPtr: number, length: number) => void;
2258
+ simdAbsF64: (aPtr: number, resultPtr: number, length: number) => void;
2259
+ simdDotF64: (aPtr: number, bPtr: number, length: number) => number;
2260
+ simdSumF64: (aPtr: number, length: number) => number;
2261
+ simdNormF64: (aPtr: number, length: number) => number;
2262
+ simdMatMulF64: (aPtr: number, bPtr: number, cPtr: number, m: number, k: number, n: number) => void;
2263
+ simdMinF64: (aPtr: number, length: number) => number;
2264
+ simdMaxF64: (aPtr: number, length: number) => number;
2265
+ simdMeanF64: (aPtr: number, length: number) => number;
2266
+ simdVarianceF64: (aPtr: number, length: number, ddof: number) => number;
2267
+ simdStdF64: (aPtr: number, length: number, ddof: number) => number;
2268
+ luDecomposition: (aPtr: number, n: number, permPtr: number) => number;
2269
+ qrDecomposition: (aPtr: number, m: number, n: number, qPtr: number) => void;
2270
+ choleskyDecomposition: (aPtr: number, n: number, lPtr: number) => number;
2271
+ eigsSymmetric: (matrixPtr: number, n: number, precision: number, eigenvaluesPtr: number, eigenvectorsPtr: number, workPtr: number) => number;
2272
+ laInv: (aPtr: number, n: number, resultPtr: number, workPtr: number) => number;
2273
+ laDet: (aPtr: number, n: number, workPtr: number) => number;
2274
+ laSolve: (aPtr: number, bPtr: number, n: number, resultPtr: number, workPtr: number) => number;
2275
+ fft: (dataPtr: number, n: number, inverse: number) => void;
2276
+ fft2d: (dataPtr: number, rows: number, cols: number, inverse: number) => void;
2277
+ convolve: (signalPtr: number, n: number, kernelPtr: number, m: number, resultPtr: number) => void;
2278
+ rfft: (dataPtr: number, n: number, resultPtr: number) => void;
2279
+ statsMean: (aPtr: number, n: number) => number;
2280
+ statsMedian: (aPtr: number, n: number) => number;
2281
+ statsVariance: (aPtr: number, n: number, ddof: number) => number;
2282
+ statsStd: (aPtr: number, n: number, ddof: number) => number;
2283
+ statsSum: (aPtr: number, n: number) => number;
2284
+ statsMin: (aPtr: number, n: number) => number;
2285
+ statsMax: (aPtr: number, n: number) => number;
2286
+ rust_mat_mul_2x2: (aPtr: number, bPtr: number, outPtr: number) => void;
2287
+ rust_fft_4: (inPtr: number, outPtr: number) => void;
2288
+ rust_gamma: (x: number, outPtr: number) => void;
2289
+ [key: string]: unknown;
2290
+ }
2291
+ /**
2292
+ * Loading metrics for performance monitoring
1952
2293
  */
1953
- interface GPUMatrixBackendConfig {
1954
- /** Minimum elements to use GPU (default: 65536 = 256x256) */
1955
- minElements?: number;
1956
- /** Use global GPU backend instance */
1957
- useGlobalBackend?: boolean;
1958
- /** GPU backend options */
1959
- gpuOptions?: GPUBackendOptions;
1960
- /** Fall back to JS on GPU errors */
1961
- fallbackOnError?: boolean;
2294
+ interface RustLoadingMetrics {
2295
+ loadMs: number;
2296
+ compileMs: number;
2297
+ instantiateMs: number;
2298
+ totalMs: number;
2299
+ binarySize: number;
1962
2300
  }
1963
2301
  /**
1964
- * GPU Matrix Backend
1965
- *
1966
- * Implements MatrixBackend interface using WebGPU compute shaders.
1967
- * Provides significant acceleration for large matrices.
1968
- *
1969
- * @example
1970
- * ```typescript
1971
- * const gpu = new GPUMatrixBackend();
1972
- * await gpu.initialize();
2302
+ * Loader for the Rust-compiled WASM module.
1973
2303
  *
1974
- * const result = gpu.multiply(matrixA, matrixB);
1975
- * ```
2304
+ * Singleton pattern with lazy loading. The WASM binary is loaded
2305
+ * on first use and cached for subsequent calls.
1976
2306
  */
1977
- declare class GPUMatrixBackend implements MatrixBackend {
1978
- readonly type: BackendType;
1979
- private config;
1980
- private backend;
1981
- private capabilities;
1982
- private initPromise;
1983
- private _available;
1984
- constructor(config?: GPUMatrixBackendConfig);
2307
+ declare class RustWasmLoader {
2308
+ private static instance;
2309
+ private wasmInstance;
2310
+ private wasmMemory;
2311
+ private allocator;
2312
+ private _isLoaded;
2313
+ private loading;
2314
+ private lastMetrics;
2315
+ private constructor();
2316
+ static getInstance(): RustWasmLoader;
2317
+ get isLoaded(): boolean;
1985
2318
  /**
1986
- * Check if GPU is available in the current environment
2319
+ * Load the Rust WASM module.
2320
+ * Returns true on success, false if the binary is not available.
2321
+ * Safe to call multiple times (idempotent).
1987
2322
  */
1988
- isAvailable(): boolean;
2323
+ load(wasmPath?: string): Promise<boolean>;
2324
+ private doLoad;
1989
2325
  /**
1990
- * Initialize the GPU backend
2326
+ * Resolve the WASM binary path.
2327
+ * Checks several locations relative to the project root.
1991
2328
  */
1992
- initialize(): Promise<void>;
1993
- private doInitialize;
2329
+ private findWasmPath;
2330
+ private getImports;
1994
2331
  /**
1995
- * Check if operation should use GPU
2332
+ * Get the typed exports from the WASM instance.
1996
2333
  */
1997
- private shouldUseGPU;
2334
+ getExports(): RustWasmExports | null;
1998
2335
  /**
1999
- * Execute GPU operation with fallback
2336
+ * Get WASM linear memory.
2000
2337
  */
2001
- private executeWithFallback;
2338
+ getMemory(): WebAssembly.Memory | null;
2002
2339
  /**
2003
- * Get GPU capabilities
2340
+ * Get loading metrics.
2004
2341
  */
2005
- getCapabilities(): GPUCapabilities | null;
2342
+ getLoadingMetrics(): RustLoadingMetrics | null;
2006
2343
  /**
2007
- * Get backend statistics
2344
+ * Write a Float64Array into WASM memory and return the pointer.
2008
2345
  */
2009
- getStats(): ReturnType<GPUBackend['getStats']> | null;
2010
- add(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2346
+ writeF64(data: Float64Array | number[]): number;
2011
2347
  /**
2012
- * Async add operation using GPU
2348
+ * Allocate an empty Float64Array in WASM memory (for output buffers).
2349
+ * Returns the pointer.
2013
2350
  */
2014
- addAsync(a: DenseMatrix, b: DenseMatrix): Promise<DenseMatrix>;
2015
- subtract(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2016
- multiplyElementwise(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2017
- divideElementwise(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2018
- scale(a: DenseMatrix, scalar: number): DenseMatrix;
2351
+ allocF64(length: number): number;
2019
2352
  /**
2020
- * Async scale operation using GPU
2353
+ * Write an Int32Array into WASM memory and return the pointer.
2021
2354
  */
2022
- scaleAsync(a: DenseMatrix, scalar: number): Promise<DenseMatrix>;
2023
- abs(a: DenseMatrix): DenseMatrix;
2024
- negate(a: DenseMatrix): DenseMatrix;
2025
- multiply(a: DenseMatrix, b: DenseMatrix): DenseMatrix;
2355
+ writeI32(data: Int32Array | number[]): number;
2026
2356
  /**
2027
- * Async matrix multiplication using GPU
2357
+ * Allocate an empty Int32Array in WASM memory.
2028
2358
  */
2029
- multiplyAsync(a: DenseMatrix, b: DenseMatrix): Promise<DenseMatrix>;
2030
- transpose(a: DenseMatrix): DenseMatrix;
2359
+ allocI32(length: number): number;
2031
2360
  /**
2032
- * Async transpose using GPU
2361
+ * Read a Float64Array from WASM memory.
2362
+ * Note: the returned array is a *copy* (safe after memory reset).
2033
2363
  */
2034
- transposeAsync(a: DenseMatrix): Promise<DenseMatrix>;
2035
- sum(a: DenseMatrix): number;
2036
- sumAxis(a: DenseMatrix, axis: 0 | 1): DenseMatrix;
2037
- norm(a: DenseMatrix): number;
2038
- dot(a: DenseMatrix, b: DenseMatrix): number;
2364
+ readF64(ptr: number, length: number): Float64Array;
2039
2365
  /**
2040
- * Update configuration
2366
+ * Read an Int32Array from WASM memory.
2041
2367
  */
2042
- updateConfig(config: Partial<GPUMatrixBackendConfig>): void;
2368
+ readI32(ptr: number, length: number): Int32Array;
2043
2369
  /**
2044
- * Get current configuration
2370
+ * Reset the bump allocator. Call between independent operations
2371
+ * to reclaim temporary memory.
2045
2372
  */
2046
- getConfig(): Required<GPUMatrixBackendConfig>;
2373
+ resetAllocator(): void;
2047
2374
  /**
2048
- * Destroy the backend
2375
+ * Reset the loader (for testing).
2049
2376
  */
2050
- destroy(): void;
2377
+ reset(): void;
2378
+ /**
2379
+ * Reset the singleton (for testing).
2380
+ */
2381
+ static resetInstance(): void;
2051
2382
  }
2052
2383
  /**
2053
- * Global GPU matrix backend instance
2384
+ * Global Rust WASM loader instance
2054
2385
  */
2055
- declare const gpuMatrixBackend: GPUMatrixBackend;
2386
+ declare const rustWasmLoader: RustWasmLoader;
2056
2387
  /**
2057
- * Create a GPU matrix backend with custom configuration
2388
+ * Initialize the Rust WASM module (call once at startup).
2389
+ * Returns true if loaded successfully, false if not available.
2058
2390
  */
2059
- declare function createGPUMatrixBackend(config?: GPUMatrixBackendConfig): GPUMatrixBackend;
2391
+ declare function initRustWasm(wasmPath?: string): Promise<boolean>;
2392
+
2393
+ /**
2394
+ * MathTS Matrix Configuration
2395
+ *
2396
+ * Centralized configuration for matrix operations, backend selection,
2397
+ * and performance tuning.
2398
+ *
2399
+ * @packageDocumentation
2400
+ */
2401
+
2402
+ /**
2403
+ * Operation type hints for backend selection.
2404
+ *
2405
+ * Defined here rather than in `BackendManager.ts` so that `config.ts` (the
2406
+ * lower-level module) owns it — `BackendManager` already imports `config`, so
2407
+ * sourcing the type the other way round closed an import cycle.
2408
+ */
2409
+ type OperationType = 'add' | 'subtract' | 'multiply' | 'multiplyElementwise' | 'transpose' | 'scale' | 'decomposition' | 'solve' | 'fft' | 'eig' | 'svd';
2060
2410
 
2061
2411
  /**
2062
2412
  * Backend Manager
@@ -2068,10 +2418,6 @@ declare function createGPUMatrixBackend(config?: GPUMatrixBackendConfig): GPUMat
2068
2418
  * @packageDocumentation
2069
2419
  */
2070
2420
 
2071
- /**
2072
- * Operation type hints for backend selection
2073
- */
2074
- type OperationType = 'add' | 'subtract' | 'multiply' | 'multiplyElementwise' | 'transpose' | 'scale' | 'decomposition' | 'solve';
2075
2421
  /**
2076
2422
  * Extended backend hints with operation-specific thresholds
2077
2423
  */
@@ -2080,11 +2426,16 @@ interface ExtendedBackendHints extends BackendHints {
2080
2426
  operationThresholds?: Partial<Record<OperationType, {
2081
2427
  wasm?: number;
2082
2428
  gpu?: number;
2429
+ rustWasm?: number;
2083
2430
  }>>;
2084
2431
  /** Enable automatic SIMD detection for WASM */
2085
2432
  autoSIMD?: boolean;
2086
2433
  /** Fallback to JS on backend failure */
2087
2434
  fallbackOnError?: boolean;
2435
+ /** Minimum elements to use Rust WASM backend (default: 1000) */
2436
+ rustWasmThreshold?: number;
2437
+ /** Operations that always prefer Rust WASM regardless of size */
2438
+ rustWasmPreferredOps?: OperationType[];
2088
2439
  }
2089
2440
  /**
2090
2441
  * Default extended hints
@@ -2122,7 +2473,15 @@ declare class BackendManager {
2122
2473
  */
2123
2474
  getHints(): Required<ExtendedBackendHints>;
2124
2475
  /**
2125
- * Get the best backend for a given operation and matrix size
2476
+ * Get the best backend for a given operation and matrix size.
2477
+ *
2478
+ * Selection priority:
2479
+ * 1. Preferred backend (if explicitly set)
2480
+ * 2. Heavy operations (fft, eig, svd, decomposition) -> Rust WASM (if loaded)
2481
+ * 3. Elements > gpuThreshold -> GPU (if available)
2482
+ * 4. Elements > rustWasmThreshold -> Rust WASM (if loaded)
2483
+ * 5. Elements > wasmThreshold -> AS WASM (if loaded)
2484
+ * 6. JS fallback
2126
2485
  */
2127
2486
  selectBackend(elementCount: number, operation?: OperationType): MatrixBackend;
2128
2487
  /**
@@ -2350,7 +2709,7 @@ declare function singularValues(matrix: number[][] | Float64Array, options?: Omi
2350
2709
  /**
2351
2710
  * Compute the pseudoinverse (Moore-Penrose inverse) using SVD
2352
2711
  */
2353
- declare function pinv(matrix: number[][], options?: SVDOptions): number[][];
2712
+ declare function pinv$1(matrix: number[][], options?: SVDOptions): number[][];
2354
2713
  /**
2355
2714
  * Low-rank approximation using SVD
2356
2715
  * Keeps only the top r singular values
@@ -2425,32 +2784,380 @@ declare function spectralRadiusWasm(matrix: number[][], options?: {
2425
2784
  }): Promise<number>;
2426
2785
 
2427
2786
  /**
2428
- * WASM-accelerated Singular Value Decomposition
2787
+ * WASM-accelerated Singular Value Decomposition.
2429
2788
  *
2430
- * Provides SVD computation with optional WASM acceleration.
2431
- * The Rust WASM crate currently exposes eigenvalue operations but not
2432
- * a direct SVD implementation. For symmetric matrices, SVD can be
2433
- * derived from eigendecomposition (singular values = |eigenvalues|).
2789
+ * Routes through the Rust WASM crate's direct one-sided Jacobi SVD
2790
+ * (`svd` export) for any real `m x n` matrix, and falls back to the
2791
+ * synchronous JavaScript Golub-Reinsch {@link svd} when the WASM module is
2792
+ * unavailable.
2434
2793
  *
2435
- * Strategy:
2436
- * - Symmetric matrices: WASM eig -> derive SVD
2437
- * - General matrices: JS Golub-Reinsch bidiagonalization (svd.ts)
2794
+ * Unlike the synchronous {@link svd} (which returns the *full* `m x m` /
2795
+ * `n x n` factors), `svdWasm` always returns the **thin / economy** form —
2796
+ * `U` is `m x k`, `V` is `n x k`, `k = min(m, n)` — on both the WASM and the
2797
+ * fallback path, so callers get a stable result shape.
2438
2798
  *
2439
2799
  * @packageDocumentation
2440
2800
  */
2441
2801
 
2442
2802
  /**
2443
- * WASM-accelerated SVD.
2444
- *
2445
- * For symmetric matrices, uses WASM eigendecomposition to derive SVD.
2446
- * For general matrices, falls back to the JavaScript Golub-Reinsch algorithm.
2803
+ * WASM-accelerated thin SVD. Always safe to call — falls back to the
2804
+ * synchronous JS SVD when the Rust WASM module is not available.
2447
2805
  *
2448
- * @param matrix - Input matrix (m x n) as 2D array
2449
- * @param options - SVD computation options
2450
- * @returns SVD decomposition { U, S, V, rank }
2806
+ * @param matrix - Input matrix (m x n) as a row-major 2D array
2807
+ * @param options - SVD options; `rankTolerance` controls the rank estimate
2808
+ * @returns thin SVD `{ U (m x k), S (k), V (n x k), rank }`
2451
2809
  */
2452
2810
  declare function svdWasm(matrix: number[][], options?: SVDOptions): Promise<SVDResult>;
2453
2811
 
2812
+ /**
2813
+ * Moore-Penrose Pseudoinverse (DenseMatrix primitive)
2814
+ *
2815
+ * Computes the pseudoinverse A⁺ of a DenseMatrix A via full SVD with
2816
+ * rcond·max(S) singular-value thresholding.
2817
+ *
2818
+ * Algorithm:
2819
+ * 1. Full SVD: A = U · diag(S) · Vᵀ (A is m×n)
2820
+ * U: m×m orthogonal, V: n×n orthogonal, S: min(m,n) values (descending).
2821
+ * 2. Threshold: s_inv_i = 1/s_i if s_i > rcond·max(S), else 0.
2822
+ * 3. Build: A⁺ = V · diag(s_inv) · Uᵀ (shape: n×m).
2823
+ *
2824
+ * Satisfies all four Moore-Penrose identities within numerical precision:
2825
+ * A · A⁺ · A = A
2826
+ * A⁺ · A · A⁺ = A⁺
2827
+ * (A · A⁺)ᵀ = A · A⁺
2828
+ * (A⁺ · A)ᵀ = A⁺ · A
2829
+ */
2830
+
2831
+ interface PinvOptions {
2832
+ /**
2833
+ * Relative condition threshold for singular-value truncation.
2834
+ * A singular value s_i is treated as zero when s_i ≤ rcond · max(S).
2835
+ * Default: 1e-10.
2836
+ */
2837
+ rcond?: number;
2838
+ }
2839
+ /**
2840
+ * Compute the Moore-Penrose pseudoinverse of a DenseMatrix.
2841
+ *
2842
+ * @param A - Input matrix (m × n).
2843
+ * @param opts - Optional rcond threshold (default 1e-10).
2844
+ * @returns A⁺, the pseudoinverse of A (n × m).
2845
+ */
2846
+ declare function pinv(A: DenseMatrix, opts?: PinvOptions): DenseMatrix;
2847
+
2848
+ /**
2849
+ * QR Decomposition (DenseMatrix primitive)
2850
+ *
2851
+ * Classical Gram-Schmidt with re-orthogonalisation. Adequate for the
2852
+ * well-conditioned matrices that arise in the tensor wrappers + the
2853
+ * `randomTensor` orthogonal-distribution code path. For pathological
2854
+ * matrices the Householder QR implemented in `WASMBackend.qrDecompositionJS`
2855
+ * is preferable, but Gram-Schmidt suffices for the current call sites.
2856
+ *
2857
+ * Two modes:
2858
+ * - 'reduced' (thin QR): Q is (m × k), R is (k × n), k = min(m, n).
2859
+ * - 'full' : Q is (m × m), R is (m × n).
2860
+ *
2861
+ * In 'reduced' mode A = Q · R reconstructs A to within `1e-12`.
2862
+ * Q's columns are orthonormal (Qᵀ · Q = I_k); R is upper-triangular.
2863
+ */
2864
+
2865
+ interface QRResult {
2866
+ /** Orthonormal Q factor. Reduced: (m × k); full: (m × m). */
2867
+ Q: DenseMatrix;
2868
+ /** Upper-triangular R factor. Reduced: (k × n); full: (m × n). */
2869
+ R: DenseMatrix;
2870
+ }
2871
+ interface QROptions {
2872
+ /** 'reduced' (default, thin QR) or 'full'. */
2873
+ mode?: 'reduced' | 'full';
2874
+ }
2875
+ /**
2876
+ * Compute the QR decomposition of `A` such that `A = Q · R`.
2877
+ *
2878
+ * @param A - Input matrix (m × n, m ≥ 0, n ≥ 0).
2879
+ * @param opts - Optional mode selector (`'reduced'` thin QR or `'full'` square Q).
2880
+ */
2881
+ declare function qr(A: DenseMatrix, opts?: QROptions): QRResult;
2882
+
2883
+ /**
2884
+ * LU Decomposition (DenseMatrix primitive)
2885
+ *
2886
+ * Doolittle's algorithm with partial (row) pivoting. Factorises a square
2887
+ * matrix A into P · A = L · U where:
2888
+ * - L is unit lower-triangular (1s on the diagonal).
2889
+ * - U is upper-triangular.
2890
+ * - P is returned as a row-permutation array: P[i] is the original-row
2891
+ * index now at position i after pivoting.
2892
+ *
2893
+ * Usage:
2894
+ * const { L, U, P } = lu(A);
2895
+ * // P[i] gives the original row moved to position i, so P · A = L · U.
2896
+ */
2897
+
2898
+ interface LUResult {
2899
+ /** Unit lower-triangular factor L. */
2900
+ L: DenseMatrix;
2901
+ /** Upper-triangular factor U. */
2902
+ U: DenseMatrix;
2903
+ /** Row permutation array of length n. P[i] is the original-row index now at position i. */
2904
+ P: number[];
2905
+ }
2906
+ /**
2907
+ * Perform LU decomposition with partial pivoting on a square `DenseMatrix`.
2908
+ *
2909
+ * Implements Doolittle's algorithm in compact form: the working array stores
2910
+ * L below the diagonal (unit diagonal implicit) and U on and above it.
2911
+ *
2912
+ * @throws {Error} if `A` is not square.
2913
+ * @throws {Error} if `A` is singular (zero pivot encountered).
2914
+ */
2915
+ declare function lu(A: DenseMatrix): LUResult;
2916
+
2917
+ /**
2918
+ * Cholesky Decomposition (DenseMatrix primitive)
2919
+ *
2920
+ * Right-looking algorithm. Factorises a symmetric positive-definite (SPD)
2921
+ * matrix A into A = L · Lᵀ where L is lower-triangular.
2922
+ *
2923
+ * Usage:
2924
+ * const { L } = cholesky(A);
2925
+ * // A ≈ L · L^T (to floating-point precision)
2926
+ */
2927
+
2928
+ interface CholeskyResult {
2929
+ /** Lower-triangular Cholesky factor L such that A = L · Lᵀ. */
2930
+ L: DenseMatrix;
2931
+ }
2932
+ /**
2933
+ * Compute the Cholesky decomposition of the symmetric positive-definite
2934
+ * `DenseMatrix` A such that A = L · Lᵀ.
2935
+ *
2936
+ * @throws {Error} if `A` is not square.
2937
+ * @throws {Error} if `A` is not positive definite (non-positive diagonal pivot).
2938
+ */
2939
+ declare function cholesky(A: DenseMatrix): CholeskyResult;
2940
+
2941
+ /**
2942
+ * Matrix Exponential — Scaling-and-Squaring with Padé-13 Approximant
2943
+ *
2944
+ * Implements Algorithm 10.20 from:
2945
+ * Higham, N. J. (2005). "The scaling and squaring method for the matrix
2946
+ * exponential revisited." SIAM J. Matrix Anal. Appl., 26(4), 1179–1193.
2947
+ *
2948
+ * Algorithm:
2949
+ * 1. Compute s = max(0, ceil(log2(||A||_1 / θ_13))) where θ_13 ≈ 5.372.
2950
+ * 2. Scale: B = A / 2^s.
2951
+ * 3. Compute the [13/13] Padé approximant R(B) = (U + V)^{-1} * (-U + V).
2952
+ * 4. Square s times: expm(A) = R(B)^(2^s).
2953
+ *
2954
+ * Works for any real square DenseMatrix. For large ||A||, uses scaling to
2955
+ * stay within the Padé approximant's accuracy radius.
2956
+ */
2957
+
2958
+ interface ExpmOptions {
2959
+ /**
2960
+ * When true, return the result as a DenseMatrix.
2961
+ * When false (default), work directly on the internal number[][] and
2962
+ * return as DenseMatrix anyway — this option is reserved for future use.
2963
+ */
2964
+ _reserved?: never;
2965
+ }
2966
+ /**
2967
+ * Compute the matrix exponential of a square DenseMatrix.
2968
+ *
2969
+ * Uses the Padé-13 scaling-and-squaring algorithm (Higham 2005).
2970
+ * Accurate to near machine precision for general real matrices.
2971
+ *
2972
+ * @param A - Square DenseMatrix (n × n).
2973
+ * @returns expm(A) as a DenseMatrix (n × n).
2974
+ * @throws Error if A is not square.
2975
+ *
2976
+ * @example
2977
+ * // expm(0) = I
2978
+ * matrixExpm(DenseMatrix.zeros(3, 3)) // => identity 3×3
2979
+ *
2980
+ * @example
2981
+ * // expm(t*I) = e^t * I
2982
+ * const tI = DenseMatrix.fromArray([[2,0],[0,2]]);
2983
+ * matrixExpm(tI) // => [[e^2, 0], [0, e^2]]
2984
+ */
2985
+ declare function matrixExpm(A: DenseMatrix): DenseMatrix;
2986
+
2987
+ /**
2988
+ * Matrix Logarithm — Schur-Padé inverse scaling-and-squaring (Slices 5.9a + 6.1)
2989
+ *
2990
+ * Implements the Schur-Padé algorithm based on:
2991
+ * Higham (2008) "Functions of Matrices: Theory and Computation," Chapter 11
2992
+ * (Algorithm 11.10).
2993
+ *
2994
+ * Algorithm (general Schur-based path, Slice 6.1):
2995
+ * 1. Schur decompose: A = Q · T · Q^T.
2996
+ * 2. Repeatedly take matrix square roots of T (Björck recurrence on upper-
2997
+ * triangular matrices) until ||T^{1/2^k} - I||_1 < 0.25.
2998
+ * 3. Evaluate log(I + X) via 16-point Gauss-Legendre quadrature.
2999
+ * 4. Scale back by 2^k; rotate by Q: logm(A) = Q · (2^k · log(T^{1/2^k})) · Q^T.
3000
+ *
3001
+ * For the eig-based fallback (diagonalisable matrices with positive real
3002
+ * eigenvalues): logm(A) = V · diag(log(λ)) · V^{-1}.
3003
+ */
3004
+
3005
+ interface LogmOptions {
3006
+ /**
3007
+ * Tolerance for the "near-identity" test.
3008
+ * Default: 0.25 (||M - I||_1 < tol triggers Padé path).
3009
+ */
3010
+ nearIdentityTol?: number;
3011
+ }
3012
+ /**
3013
+ * Compute the principal matrix logarithm of a square DenseMatrix.
3014
+ *
3015
+ * Algorithm (Slice 5.9a — inverse scaling-and-squaring + Padé quadrature):
3016
+ * 1. Repeatedly take matrix square roots until ||M - I||_1 < nearIdentityTol.
3017
+ * 2. Evaluate log(I + X) = X * ∫₀¹ (I + tX)^{-1} dt via 7-pt Gauss-Legendre.
3018
+ * 3. Scale back: logm(A) = 2^k * log(A^{1/2^k}).
3019
+ *
3020
+ * Falls back to eigendecomposition if the square-root sequence diverges
3021
+ * (i.e., if the matrix has no non-positive eigenvalues and is diagonalisable).
3022
+ *
3023
+ * Limitations (deferred to Slice 5.9b):
3024
+ * - Matrices with non-positive real eigenvalues: principal log is undefined.
3025
+ * - Matrices with complex eigenvalues: throws.
3026
+ * - Non-diagonalisable (defective) matrices: eig-fallback also throws.
3027
+ * - Full Schur-based inverse-scaling-and-squaring for general non-normal
3028
+ * matrices.
3029
+ *
3030
+ * @param A - Square DenseMatrix with positive real eigenvalues.
3031
+ * @returns logm(A) as a DenseMatrix.
3032
+ * @throws Error for matrices with non-positive or complex eigenvalues.
3033
+ *
3034
+ * @example
3035
+ * // logm(I) = 0
3036
+ * matrixLogm(DenseMatrix.eye(3)) // => zero matrix
3037
+ *
3038
+ * @example
3039
+ * // Round-trip: expm(logm(A)) ≈ A
3040
+ * const A = DenseMatrix.fromArray([[4, 1], [0, 9]]);
3041
+ * const logA = matrixLogm(A);
3042
+ * // expm(logA) ≈ A (to machine precision for diagonalisable A)
3043
+ */
3044
+ declare function matrixLogm(A: DenseMatrix, opts?: LogmOptions): DenseMatrix;
3045
+
3046
+ /**
3047
+ * Matrix Square Root — Hybrid approach (Slices 5.9a + 6.1)
3048
+ *
3049
+ * Computes the principal square root of a square matrix.
3050
+ *
3051
+ * Algorithm selection:
3052
+ * 1. For symmetric positive semi-definite matrices: symmetric eigendecomposition
3053
+ * with Gram-Schmidt re-orthogonalisation (handles repeated eigenvalues).
3054
+ * 2. For general matrices: Björck-Hammarling Schur-based algorithm
3055
+ * (Higham 2008, Algorithm 6.3):
3056
+ * a. Schur decompose: A = Q · T · Q^T.
3057
+ * b. Compute upper-triangular U with U^2 = T via back-substitution.
3058
+ * c. Rotate back: sqrtm(A) = Q · U · Q^T.
3059
+ * Falls back to Newton iteration for diagonalisable matrices when the
3060
+ * Schur path is unsuitable (e.g. negative eigenvalues in 1×1 blocks).
3061
+ *
3062
+ * References:
3063
+ * - Higham (2008) "Functions of Matrices" §6 (Algorithm 6.3).
3064
+ * - Björck & Hammarling (1983) "A Schur method for the square root of a matrix."
3065
+ */
3066
+
3067
+ interface SqrtmOptions {
3068
+ /**
3069
+ * Force the symmetric-eigendecomposition path even for non-SPD matrices.
3070
+ * By default, symmetry is auto-detected.
3071
+ */
3072
+ assumeSymmetric?: boolean;
3073
+ }
3074
+ /**
3075
+ * Compute the principal square root of a square DenseMatrix.
3076
+ *
3077
+ * For symmetric positive semi-definite A:
3078
+ * Uses symmetric eigendecomposition with Gram-Schmidt re-orthogonalisation.
3079
+ *
3080
+ * For general diagonalisable A with non-negative eigenvalues:
3081
+ * Uses Newton iteration Y_{k+1} = (Y_k + A * Y_k^{-1}) / 2, falling back
3082
+ * to the eig-based formula if Newton fails to converge.
3083
+ *
3084
+ * Slice 5.9a limitations:
3085
+ * - Matrices with negative real eigenvalues: throws.
3086
+ * - Matrices with complex eigenvalues: throws.
3087
+ * - Non-diagonalisable (defective) matrices: Newton may fail + eig fallback
3088
+ * may also fail. Full Schur-based Björck-Hammarling deferred to Slice 5.9b.
3089
+ *
3090
+ * @param A - Square DenseMatrix (n × n).
3091
+ * @param opts - Optional flags.
3092
+ * @returns sqrtm(A), the principal square root.
3093
+ * @throws Error for matrices with negative or complex eigenvalues.
3094
+ *
3095
+ * @example
3096
+ * // sqrtm(I) = I
3097
+ * matrixSqrtm(DenseMatrix.eye(3)) // => identity 3×3
3098
+ *
3099
+ * @example
3100
+ * // sqrtm(4*I) = 2*I
3101
+ * const A = DenseMatrix.fromArray([[4,0],[0,4]]);
3102
+ * matrixSqrtm(A) // => [[2,0],[0,2]]
3103
+ *
3104
+ * @example
3105
+ * // Round-trip: sqrtm(A)^2 ≈ A
3106
+ * const S = DenseMatrix.fromArray([[4,2],[2,3]]);
3107
+ * const R = matrixSqrtm(S);
3108
+ * // R * R ≈ S (to machine precision for SPD matrices)
3109
+ */
3110
+ declare function matrixSqrtm(A: DenseMatrix, opts?: SqrtmOptions): DenseMatrix;
3111
+
3112
+ /**
3113
+ * Schur Decomposition — Francis QR with double shifts (Slice 6.1)
3114
+ *
3115
+ * Computes the real Schur decomposition A = Q · T · Q^T where:
3116
+ * - Q is orthogonal (Q^T · Q = I)
3117
+ * - T is quasi-upper-triangular (real Schur form): diagonal blocks are
3118
+ * 1×1 (real eigenvalue) or 2×2 (complex-conjugate eigenvalue pair)
3119
+ *
3120
+ * Algorithm: Householder reduction to upper Hessenberg form followed by
3121
+ * Francis double-shift implicit QR iteration (Golub & Van Loan §7.5).
3122
+ *
3123
+ * References:
3124
+ * Golub & Van Loan (2013) "Matrix Computations," 4th ed., §7.5.
3125
+ * Higham (2008) "Functions of Matrices: Theory and Computation," §1.
3126
+ */
3127
+
3128
+ interface SchurResult {
3129
+ /** Orthogonal factor Q (Q^T · Q = I, Q · Q^T = I). */
3130
+ Q: DenseMatrix;
3131
+ /** Quasi-upper-triangular Schur form T (real Schur form). */
3132
+ T: DenseMatrix;
3133
+ }
3134
+ interface SchurOptions {
3135
+ /** Maximum QR iterations (default: 1000). */
3136
+ maxIterations?: number;
3137
+ /** Deflation tolerance (default: 1e-12). */
3138
+ tolerance?: number;
3139
+ }
3140
+ /**
3141
+ * Compute the real Schur decomposition of a square matrix:
3142
+ * A = Q · T · Q^T
3143
+ *
3144
+ * T is quasi-upper-triangular (real Schur form): 1×1 diagonal blocks for
3145
+ * real eigenvalues and 2×2 blocks for complex-conjugate pairs. Q is
3146
+ * orthogonal.
3147
+ *
3148
+ * For matrices with all real eigenvalues, T is upper triangular with
3149
+ * eigenvalues on the diagonal. For matrices with complex-conjugate eigenvalue
3150
+ * pairs, the corresponding 2×2 diagonal block has the form
3151
+ * [[a, b], [-b, a]] (approximately)
3152
+ * and the complex pair is a ± bi.
3153
+ *
3154
+ * @param A - Square DenseMatrix (n × n, real entries).
3155
+ * @param opts - Optional algorithm parameters.
3156
+ * @returns { Q, T } satisfying Q · T · Q^T ≈ A.
3157
+ * @throws Error if A is not square.
3158
+ */
3159
+ declare function matrixSchur(A: DenseMatrix, opts?: SchurOptions): SchurResult;
3160
+
2454
3161
  /**
2455
3162
  * Typed Matrix Operations
2456
3163
  *
@@ -2834,4 +3541,4 @@ declare function initializeParallelMatrix(): Promise<void>;
2834
3541
  */
2835
3542
  declare function terminateParallelMatrix(): Promise<void>;
2836
3543
 
2837
- export { BUILTIN_SHADERS, type BackendHints, BackendManager, BackendRegistry, type BackendType, BatchExecutor, BufferPool, DEFAULT_BACKEND_HINTS, DEFAULT_EXTENDED_HINTS, DenseMatrix, type EigOptions, type EigResult, type ExtendedBackendHints, GPUBackend, type GPUBackendOptions, type GPUBackendStatus, type GPUCapabilities, GPUContext, type GPUContextOptions, GPUMatrixBackend, type GPUMatrixBackendConfig, JSBackend, Matrix, type MatrixBackend, type MatrixDimensions, type MatrixEntry, type MatrixIndex, type MatrixType, type OperationType, ParallelBackend, type ParallelBackendConfig, type SVDOptions, type SVDResult, ShaderManager, type SliceSpec, SparseMatrix, type SyncConfig, SyncManager, type SyncStrategy, WASMBackend, type WASMBackendConfig, type WasmFeatures, abs, add, backendManager, backendRegistry, clearFeatureCache, column, cond, createBackendManager, createGPUMatrixBackend, createParallelBackend, createSyncManager, createWASMBackend, destroyGlobalGPU, destroyGlobalGPUBackend, detectGPUCapabilities, detectWasmFeatures, diag, diagonal, divide, dotMultiply, eig, eigWasm, eigvals, eigvalsWasm, exp, getCachedFeatures, getGlobalGPUBackend, getGlobalGPUContext, getRecommendedWorkgroupSize, gpuMatrixBackend, hasWebGPU, identity, initializeGlobalGPUBackend, initializeParallelMatrix, isAtomicsAvailable, isDenseMatrix, isMatrix, isSharedMemoryAvailable, isSparseMatrix, isWasmAvailable, jsBackend, log, lowRankApprox, matrix, max, mean, min, multiply, norm, norm2, normFro, ones, parallelBackend, parallelDiag, parallelDotMultiply, parallelIdentity, parallelMatrix, parallelMatrixAbs, parallelMatrixAdd, parallelMatrixColumn, parallelMatrixCos, parallelMatrixDiagonal, parallelMatrixDistance, parallelMatrixDivide, parallelMatrixDot, parallelMatrixExp, parallelMatrixHistogram, parallelMatrixLog, parallelMatrixMatvec, parallelMatrixMax, parallelMatrixMean, parallelMatrixMin, parallelMatrixMultiply, parallelMatrixNorm, parallelMatrixOperations, parallelMatrixOuter, parallelMatrixRow, parallelMatrixSin, parallelMatrixSize, parallelMatrixSqrt, parallelMatrixSquare, parallelMatrixStd, parallelMatrixSubset, parallelMatrixSubtract, parallelMatrixSum, parallelMatrixTan, parallelMatrixTrace, parallelMatrixTranspose, parallelMatrixVariance, parallelOnes, parallelRandom, parallelUnaryMinus, parallelZeros, pinv, pow, powerIteration, random, row, singularValues, size, spectralRadiusWasm, sqrt, square, subset, subtract, sum, svd, svdWasm, terminateParallelMatrix, trace, transpose, typedMatrixOperations, unaryMinus, wasmBackend, zeros };
3544
+ export { BUILTIN_SHADERS, type BackendHints, BackendManager, BackendRegistry, type BackendType, BatchExecutor, BufferPool, type CholeskyResult, DEFAULT_BACKEND_HINTS, DEFAULT_EXTENDED_HINTS, DenseMatrix, type EigOptions, type EigResult, type ExpmOptions, type ExtendedBackendHints, GPUBackend, type GPUBackendOptions, type GPUBackendStatus, type GPUCapabilities, GPUContext, type GPUContextOptions, GPUMatrixBackend, type GPUMatrixBackendConfig, JSBackend, type LUResult, type LogmOptions, Matrix, type MatrixBackend, type MatrixDimensions, type MatrixEntry, type MatrixIndex, type MatrixType, type OperationType, ParallelBackend, type ParallelBackendConfig, type PinvOptions, type QROptions, type QRResult, type RustLoadingMetrics, RustWASMBackend, type RustWASMBackendConfig, type RustWasmExports, RustWasmLoader, type SVDOptions, type SVDResult, type SchurOptions, type SchurResult, ShaderManager, type SliceSpec, SparseMatrix, type SqrtmOptions, type SyncConfig, SyncManager, type SyncStrategy, WASMBackend, type WASMBackendConfig, type WasmFeatures, abs, add, backendManager, backendRegistry, cholesky, clearFeatureCache, column, cond, createBackendManager, createGPUMatrixBackend, createParallelBackend, createRustWASMBackend, createSyncManager, createWASMBackend, destroyGlobalGPU, destroyGlobalGPUBackend, detectGPUCapabilities, detectWasmFeatures, diag, diagonal, divide, dotMultiply, eig, eigWasm, eigvals, eigvalsWasm, exp, getCachedFeatures, getGlobalGPUBackend, getGlobalGPUContext, getRecommendedWorkgroupSize, gpuMatrixBackend, hasWebGPU, identity, initRustWasm, initializeGlobalGPUBackend, initializeParallelMatrix, isAtomicsAvailable, isDenseMatrix, isMatrix, isSharedMemoryAvailable, isSparseMatrix, isWasmAvailable, jsBackend, log, lowRankApprox, lu, matrix, matrixExpm, matrixLogm, pinv as matrixPinv, matrixSchur, matrixSqrtm, max, mean, min, multiply, norm, norm2, normFro, ones, parallelBackend, parallelDiag, parallelDotMultiply, parallelIdentity, parallelMatrix, parallelMatrixAbs, parallelMatrixAdd, parallelMatrixColumn, parallelMatrixCos, parallelMatrixDiagonal, parallelMatrixDistance, parallelMatrixDivide, parallelMatrixDot, parallelMatrixExp, parallelMatrixHistogram, parallelMatrixLog, parallelMatrixMatvec, parallelMatrixMax, parallelMatrixMean, parallelMatrixMin, parallelMatrixMultiply, parallelMatrixNorm, parallelMatrixOperations, parallelMatrixOuter, parallelMatrixRow, parallelMatrixSin, parallelMatrixSize, parallelMatrixSqrt, parallelMatrixSquare, parallelMatrixStd, parallelMatrixSubset, parallelMatrixSubtract, parallelMatrixSum, parallelMatrixTan, parallelMatrixTrace, parallelMatrixTranspose, parallelMatrixVariance, parallelOnes, parallelRandom, parallelUnaryMinus, parallelZeros, pinv$1 as pinv, pow, powerIteration, qr, random, row, rustWasmBackend, rustWasmLoader, singularValues, size, spectralRadiusWasm, sqrt, square, subset, subtract, sum, svd, svdWasm, terminateParallelMatrix, trace, transpose, typedMatrixOperations, unaryMinus, wasmBackend, zeros };