linreg-core 0.4.0 → 0.5.0
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/README.md +96 -14
- package/linreg_core.d.ts +137 -0
- package/linreg_core.js +237 -0
- package/linreg_core_bg.wasm +0 -0
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -4,8 +4,10 @@
|
|
|
4
4
|
[](https://github.com/jesse-anderson/linreg-core/actions/workflows/ci.yml)
|
|
5
5
|
[](LICENSE-MIT)
|
|
6
6
|
[](https://crates.io/crates/linreg-core)
|
|
7
|
+
[](https://www.npmjs.com/package/linreg-core)
|
|
8
|
+
[](https://pypi.org/project/linreg-core/)
|
|
7
9
|
[](https://docs.rs/linreg-core)
|
|
8
|
-
|
|
10
|
+
|
|
9
11
|
|
|
10
12
|
A lightweight, self-contained linear regression library written in Rust. Compiles to WebAssembly for browser use, Python bindings via PyO3, or runs as a native Rust crate.
|
|
11
13
|
|
|
@@ -30,17 +32,19 @@ A lightweight, self-contained linear regression library written in Rust. Compile
|
|
|
30
32
|
## Features
|
|
31
33
|
|
|
32
34
|
### Regression Methods
|
|
33
|
-
- **OLS Regression:** Coefficients, standard errors, t-statistics, p-values, confidence intervals
|
|
34
|
-
- **Ridge Regression:** L2-regularized regression with optional standardization
|
|
35
|
-
- **Lasso Regression:** L1-regularized regression via coordinate descent
|
|
36
|
-
- **Elastic Net:** Combined L1 + L2 regularization for variable selection with multicollinearity handling
|
|
35
|
+
- **OLS Regression:** Coefficients, standard errors, t-statistics, p-values, confidence intervals, model selection criteria (AIC, BIC, log-likelihood)
|
|
36
|
+
- **Ridge Regression:** L2-regularized regression with optional standardization, effective degrees of freedom, model selection criteria
|
|
37
|
+
- **Lasso Regression:** L1-regularized regression via coordinate descent with automatic variable selection, convergence tracking, model selection criteria
|
|
38
|
+
- **Elastic Net:** Combined L1 + L2 regularization for variable selection with multicollinearity handling, active set convergence, model selection criteria
|
|
39
|
+
- **LOESS:** Locally estimated scatterplot smoothing for non-parametric curve fitting with configurable span, polynomial degree, and robust fitting
|
|
37
40
|
- **Lambda Path Generation:** Create regularization paths for cross-validation
|
|
38
41
|
|
|
39
42
|
### Model Statistics
|
|
40
|
-
- R-squared, Adjusted R-squared, F-statistic, F-test p-value
|
|
41
|
-
-
|
|
42
|
-
-
|
|
43
|
-
-
|
|
43
|
+
- **Fit Metrics:** R-squared, Adjusted R-squared, F-statistic, F-test p-value
|
|
44
|
+
- **Error Metrics:** Mean Squared Error (MSE), Root Mean Squared Error (RMSE), Mean Absolute Error (MAE)
|
|
45
|
+
- **Model Selection:** Log-likelihood, AIC (Akaike Information Criterion), BIC (Bayesian Information Criterion)
|
|
46
|
+
- **Residuals:** Raw residuals, standardized residuals, fitted values, leverage (hat matrix diagonal)
|
|
47
|
+
- **Multicollinearity:** Variance Inflation Factor (VIF) for each predictor
|
|
44
48
|
|
|
45
49
|
### Diagnostic Tests
|
|
46
50
|
| Category | Tests |
|
|
@@ -49,7 +53,8 @@ A lightweight, self-contained linear regression library written in Rust. Compile
|
|
|
49
53
|
| **Heteroscedasticity** | Breusch-Pagan (Koenker variant), White Test (R & Python methods) |
|
|
50
54
|
| **Normality** | Jarque-Bera, Shapiro-Wilk (n ≤ 5000), Anderson-Darling |
|
|
51
55
|
| **Autocorrelation** | Durbin-Watson, Breusch-Godfrey (higher-order) |
|
|
52
|
-
| **
|
|
56
|
+
| **Multicollinearity** | Variance Inflation Factor (VIF) |
|
|
57
|
+
| **Influence** | Cook's Distance, DFBETAS, DFFITS |
|
|
53
58
|
|
|
54
59
|
---
|
|
55
60
|
|
|
@@ -59,7 +64,7 @@ Add to your `Cargo.toml`:
|
|
|
59
64
|
|
|
60
65
|
```toml
|
|
61
66
|
[dependencies]
|
|
62
|
-
linreg-core = { version = "0.
|
|
67
|
+
linreg-core = { version = "0.5", default-features = false }
|
|
63
68
|
```
|
|
64
69
|
|
|
65
70
|
### OLS Regression (Rust)
|
|
@@ -77,6 +82,9 @@ fn main() -> Result<(), linreg_core::Error> {
|
|
|
77
82
|
println!("Coefficients: {:?}", result.coefficients);
|
|
78
83
|
println!("R-squared: {:.4}", result.r_squared);
|
|
79
84
|
println!("F-statistic: {:.4}", result.f_statistic);
|
|
85
|
+
println!("Log-likelihood: {:.4}", result.log_likelihood);
|
|
86
|
+
println!("AIC: {:.4}", result.aic);
|
|
87
|
+
println!("BIC: {:.4}", result.bic);
|
|
80
88
|
|
|
81
89
|
Ok(())
|
|
82
90
|
}
|
|
@@ -107,6 +115,10 @@ fn main() -> Result<(), linreg_core::Error> {
|
|
|
107
115
|
let result = ridge_fit(&x, &y, &options)?;
|
|
108
116
|
println!("Intercept: {}", result.intercept);
|
|
109
117
|
println!("Coefficients: {:?}", result.coefficients);
|
|
118
|
+
println!("R-squared: {:.4}", result.r_squared);
|
|
119
|
+
println!("Effective degrees of freedom: {:.2}", result.effective_df);
|
|
120
|
+
println!("AIC: {:.4}", result.aic);
|
|
121
|
+
println!("BIC: {:.4}", result.bic);
|
|
110
122
|
|
|
111
123
|
Ok(())
|
|
112
124
|
}
|
|
@@ -139,6 +151,8 @@ fn main() -> Result<(), linreg_core::Error> {
|
|
|
139
151
|
println!("Intercept: {}", result.intercept);
|
|
140
152
|
println!("Coefficients: {:?}", result.coefficients);
|
|
141
153
|
println!("Non-zero coefficients: {}", result.n_nonzero);
|
|
154
|
+
println!("AIC: {:.4}", result.aic);
|
|
155
|
+
println!("BIC: {:.4}", result.bic);
|
|
142
156
|
|
|
143
157
|
Ok(())
|
|
144
158
|
}
|
|
@@ -172,6 +186,8 @@ fn main() -> Result<(), linreg_core::Error> {
|
|
|
172
186
|
println!("Intercept: {}", result.intercept);
|
|
173
187
|
println!("Coefficients: {:?}", result.coefficients);
|
|
174
188
|
println!("Non-zero coefficients: {}", result.n_nonzero);
|
|
189
|
+
println!("AIC: {:.4}", result.aic);
|
|
190
|
+
println!("BIC: {:.4}", result.bic);
|
|
175
191
|
|
|
176
192
|
Ok(())
|
|
177
193
|
}
|
|
@@ -265,6 +281,9 @@ async function run() {
|
|
|
265
281
|
const result = JSON.parse(resultJson);
|
|
266
282
|
console.log("Coefficients:", result.coefficients);
|
|
267
283
|
console.log("R-squared:", result.r_squared);
|
|
284
|
+
console.log("Log-likelihood:", result.log_likelihood);
|
|
285
|
+
console.log("AIC:", result.aic);
|
|
286
|
+
console.log("BIC:", result.bic);
|
|
268
287
|
}
|
|
269
288
|
|
|
270
289
|
run();
|
|
@@ -282,6 +301,10 @@ const result = JSON.parse(ridge_regression(
|
|
|
282
301
|
));
|
|
283
302
|
|
|
284
303
|
console.log("Coefficients:", result.coefficients);
|
|
304
|
+
console.log("R-squared:", result.r_squared);
|
|
305
|
+
console.log("Effective degrees of freedom:", result.effective_df);
|
|
306
|
+
console.log("AIC:", result.aic);
|
|
307
|
+
console.log("BIC:", result.bic);
|
|
285
308
|
```
|
|
286
309
|
|
|
287
310
|
### Lasso Regression (WASM)
|
|
@@ -299,6 +322,8 @@ const result = JSON.parse(lasso_regression(
|
|
|
299
322
|
|
|
300
323
|
console.log("Coefficients:", result.coefficients);
|
|
301
324
|
console.log("Non-zero coefficients:", result.n_nonzero);
|
|
325
|
+
console.log("AIC:", result.aic);
|
|
326
|
+
console.log("BIC:", result.bic);
|
|
302
327
|
```
|
|
303
328
|
|
|
304
329
|
### Elastic Net Regression (WASM)
|
|
@@ -317,6 +342,8 @@ const result = JSON.parse(elastic_net_regression(
|
|
|
317
342
|
|
|
318
343
|
console.log("Coefficients:", result.coefficients);
|
|
319
344
|
console.log("Non-zero coefficients:", result.n_nonzero);
|
|
345
|
+
console.log("AIC:", result.aic);
|
|
346
|
+
console.log("BIC:", result.bic);
|
|
320
347
|
```
|
|
321
348
|
|
|
322
349
|
### Lambda Path Generation (WASM)
|
|
@@ -333,6 +360,22 @@ console.log("Lambda sequence:", path.lambda_path);
|
|
|
333
360
|
console.log("Lambda max:", path.lambda_max);
|
|
334
361
|
```
|
|
335
362
|
|
|
363
|
+
### LOESS Regression (WASM)
|
|
364
|
+
|
|
365
|
+
```javascript
|
|
366
|
+
const result = JSON.parse(loess_fit(
|
|
367
|
+
JSON.stringify(y),
|
|
368
|
+
JSON.stringify(x[0]), // Single predictor only (flattened array)
|
|
369
|
+
0.5, // span (smoothing parameter: 0-1)
|
|
370
|
+
1, // degree (0=constant, 1=linear, 2=quadratic)
|
|
371
|
+
"direct", // surface method ("direct" or "interpolate")
|
|
372
|
+
0 // robust iterations (0=disabled, >0=number of iterations)
|
|
373
|
+
));
|
|
374
|
+
|
|
375
|
+
console.log("Fitted values:", result.fitted_values);
|
|
376
|
+
console.log("Residuals:", result.residuals);
|
|
377
|
+
```
|
|
378
|
+
|
|
336
379
|
### Diagnostic Tests (WASM)
|
|
337
380
|
|
|
338
381
|
```javascript
|
|
@@ -405,6 +448,25 @@ const cd = JSON.parse(cooks_distance_test(
|
|
|
405
448
|
JSON.stringify(x)
|
|
406
449
|
));
|
|
407
450
|
|
|
451
|
+
// DFBETAS (influence on coefficients)
|
|
452
|
+
const dfbetas = JSON.parse(dfbetas_test(
|
|
453
|
+
JSON.stringify(y),
|
|
454
|
+
JSON.stringify(x)
|
|
455
|
+
));
|
|
456
|
+
|
|
457
|
+
// DFFITS (influence on fitted values)
|
|
458
|
+
const dffits = JSON.parse(dffits_test(
|
|
459
|
+
JSON.stringify(y),
|
|
460
|
+
JSON.stringify(x)
|
|
461
|
+
));
|
|
462
|
+
|
|
463
|
+
// VIF test (multicollinearity)
|
|
464
|
+
const vif = JSON.parse(vif_test(
|
|
465
|
+
JSON.stringify(y),
|
|
466
|
+
JSON.stringify(x)
|
|
467
|
+
));
|
|
468
|
+
console.log("VIF values:", vif.vif_values);
|
|
469
|
+
|
|
408
470
|
// RESET test (functional form)
|
|
409
471
|
const reset = JSON.parse(reset_test(
|
|
410
472
|
JSON.stringify(y),
|
|
@@ -458,7 +520,7 @@ console.log("Numeric columns:", parsed.numeric_columns);
|
|
|
458
520
|
### Helper Functions (WASM)
|
|
459
521
|
|
|
460
522
|
```javascript
|
|
461
|
-
const version = get_version(); // e.g., "0.
|
|
523
|
+
const version = get_version(); // e.g., "0.5.0"
|
|
462
524
|
const msg = test(); // "Rust WASM is working!"
|
|
463
525
|
```
|
|
464
526
|
|
|
@@ -519,7 +581,7 @@ print(result.summary())
|
|
|
519
581
|
```
|
|
520
582
|
|
|
521
583
|
**Result objects** provide:
|
|
522
|
-
- Direct attribute access (`result.r_squared`, `result.coefficients`)
|
|
584
|
+
- Direct attribute access (`result.r_squared`, `result.coefficients`, `result.aic`, `result.bic`, `result.log_likelihood`)
|
|
523
585
|
- `summary()` method for formatted output
|
|
524
586
|
- `to_dict()` method for JSON serialization
|
|
525
587
|
|
|
@@ -536,6 +598,9 @@ result = linreg_core.ols_regression(y, x, names)
|
|
|
536
598
|
print(f"Coefficients: {result.coefficients}")
|
|
537
599
|
print(f"R-squared: {result.r_squared}")
|
|
538
600
|
print(f"F-statistic: {result.f_statistic}")
|
|
601
|
+
print(f"Log-likelihood: {result.log_likelihood}")
|
|
602
|
+
print(f"AIC: {result.aic}")
|
|
603
|
+
print(f"BIC: {result.bic}")
|
|
539
604
|
```
|
|
540
605
|
|
|
541
606
|
### Ridge Regression (Python)
|
|
@@ -548,6 +613,9 @@ result = linreg_core.ridge_regression(
|
|
|
548
613
|
)
|
|
549
614
|
print(f"Intercept: {result.intercept}")
|
|
550
615
|
print(f"Coefficients: {result.coefficients}")
|
|
616
|
+
print(f"Effective degrees of freedom: {result.effective_df:.2f}")
|
|
617
|
+
print(f"AIC: {result.aic}")
|
|
618
|
+
print(f"BIC: {result.bic}")
|
|
551
619
|
```
|
|
552
620
|
|
|
553
621
|
### Lasso Regression (Python)
|
|
@@ -564,6 +632,8 @@ print(f"Intercept: {result.intercept}")
|
|
|
564
632
|
print(f"Coefficients: {result.coefficients}")
|
|
565
633
|
print(f"Non-zero: {result.n_nonzero}")
|
|
566
634
|
print(f"Converged: {result.converged}")
|
|
635
|
+
print(f"AIC: {result.aic}")
|
|
636
|
+
print(f"BIC: {result.bic}")
|
|
567
637
|
```
|
|
568
638
|
|
|
569
639
|
### Elastic Net Regression (Python)
|
|
@@ -580,6 +650,8 @@ result = linreg_core.elastic_net_regression(
|
|
|
580
650
|
print(f"Intercept: {result.intercept}")
|
|
581
651
|
print(f"Coefficients: {result.coefficients}")
|
|
582
652
|
print(f"Non-zero: {result.n_nonzero}")
|
|
653
|
+
print(f"AIC: {result.aic}")
|
|
654
|
+
print(f"BIC: {result.bic}")
|
|
583
655
|
```
|
|
584
656
|
|
|
585
657
|
### Lambda Path Generation (Python)
|
|
@@ -631,6 +703,16 @@ ad = linreg_core.anderson_darling_test(y, x)
|
|
|
631
703
|
cd = linreg_core.cooks_distance_test(y, x)
|
|
632
704
|
print(f"Influential points: {cd.influential_4_over_n}")
|
|
633
705
|
|
|
706
|
+
# DFBETAS (influence on each coefficient)
|
|
707
|
+
dfbetas = linreg_core.dfbetas_test(y, x)
|
|
708
|
+
print(f"Threshold: {dfbetas.threshold}")
|
|
709
|
+
print(f"Influential obs: {dfbetas.influential_observations}")
|
|
710
|
+
|
|
711
|
+
# DFFITS (influence on fitted values)
|
|
712
|
+
dffits = linreg_core.dffits_test(y, x)
|
|
713
|
+
print(f"Threshold: {dffits.threshold}")
|
|
714
|
+
print(f"Influential obs: {dffits.influential_observations}")
|
|
715
|
+
|
|
634
716
|
# RESET test (model specification)
|
|
635
717
|
reset = linreg_core.reset_test(y, x, [2, 3], "fitted")
|
|
636
718
|
|
|
@@ -698,7 +780,7 @@ print(f"Data rows: {result.n_rows}")
|
|
|
698
780
|
For native Rust without WASM overhead:
|
|
699
781
|
|
|
700
782
|
```toml
|
|
701
|
-
linreg-core = { version = "0.
|
|
783
|
+
linreg-core = { version = "0.5", default-features = false }
|
|
702
784
|
```
|
|
703
785
|
|
|
704
786
|
For Python bindings (built with maturin):
|
package/linreg_core.d.ts
CHANGED
|
@@ -95,6 +95,50 @@ export function breusch_pagan_test(y_json: string, x_vars_json: string): string;
|
|
|
95
95
|
*/
|
|
96
96
|
export function cooks_distance_test(y_json: string, x_vars_json: string): string;
|
|
97
97
|
|
|
98
|
+
/**
|
|
99
|
+
* Performs DFBETAS analysis via WASM.
|
|
100
|
+
*
|
|
101
|
+
* DFBETAS measures the influence of each observation on each regression coefficient.
|
|
102
|
+
* For each observation and each coefficient, it computes the standardized change
|
|
103
|
+
* in the coefficient when that observation is omitted.
|
|
104
|
+
*
|
|
105
|
+
* # Arguments
|
|
106
|
+
*
|
|
107
|
+
* * `y_json` - JSON array of response variable values
|
|
108
|
+
* * `x_vars_json` - JSON array of predictor arrays
|
|
109
|
+
*
|
|
110
|
+
* # Returns
|
|
111
|
+
*
|
|
112
|
+
* JSON string containing the DFBETAS matrix, threshold, and influential observations.
|
|
113
|
+
*
|
|
114
|
+
* # Errors
|
|
115
|
+
*
|
|
116
|
+
* Returns a JSON error object if parsing fails or domain check fails.
|
|
117
|
+
*/
|
|
118
|
+
export function dfbetas_test(y_json: string, x_vars_json: string): string;
|
|
119
|
+
|
|
120
|
+
/**
|
|
121
|
+
* Performs DFFITS analysis via WASM.
|
|
122
|
+
*
|
|
123
|
+
* DFFITS measures the influence of each observation on its own fitted value.
|
|
124
|
+
* It is the standardized change in the fitted value when that observation
|
|
125
|
+
* is omitted from the model.
|
|
126
|
+
*
|
|
127
|
+
* # Arguments
|
|
128
|
+
*
|
|
129
|
+
* * `y_json` - JSON array of response variable values
|
|
130
|
+
* * `x_vars_json` - JSON array of predictor arrays
|
|
131
|
+
*
|
|
132
|
+
* # Returns
|
|
133
|
+
*
|
|
134
|
+
* JSON string containing the DFFITS vector, threshold, and influential observations.
|
|
135
|
+
*
|
|
136
|
+
* # Errors
|
|
137
|
+
*
|
|
138
|
+
* Returns a JSON error object if parsing fails or domain check fails.
|
|
139
|
+
*/
|
|
140
|
+
export function dffits_test(y_json: string, x_vars_json: string): string;
|
|
141
|
+
|
|
98
142
|
/**
|
|
99
143
|
* Performs the Durbin-Watson test for autocorrelation via WASM.
|
|
100
144
|
*
|
|
@@ -283,6 +327,65 @@ export function jarque_bera_test(y_json: string, x_vars_json: string): string;
|
|
|
283
327
|
*/
|
|
284
328
|
export function lasso_regression(y_json: string, x_vars_json: string, _variable_names: string, lambda: number, standardize: boolean, max_iter: number, tol: number): string;
|
|
285
329
|
|
|
330
|
+
/**
|
|
331
|
+
* Performs LOESS regression via WASM.
|
|
332
|
+
*
|
|
333
|
+
* LOESS (Locally Estimated Scatterplot Smoothing) is a non-parametric
|
|
334
|
+
* regression method that fits multiple regressions in local subsets
|
|
335
|
+
* of data to create a smooth curve through the data points.
|
|
336
|
+
*
|
|
337
|
+
* # Arguments
|
|
338
|
+
*
|
|
339
|
+
* * `y_json` - JSON array of response variable values
|
|
340
|
+
* * `x_vars_json` - JSON array of predictor arrays
|
|
341
|
+
* * `span` - Fraction of data used in each local fit (0.0 to 1.0)
|
|
342
|
+
* * `degree` - Degree of local polynomial: 0 (constant), 1 (linear), or 2 (quadratic)
|
|
343
|
+
* * `robust_iterations` - Number of robustness iterations (0 for non-robust fit)
|
|
344
|
+
* * `surface` - Surface computation method: "direct" or "interpolate"
|
|
345
|
+
*
|
|
346
|
+
* # Returns
|
|
347
|
+
*
|
|
348
|
+
* JSON string containing:
|
|
349
|
+
* - `fitted` - Fitted values at each observation point
|
|
350
|
+
* - `span` - Span parameter used
|
|
351
|
+
* - `degree` - Degree of polynomial used
|
|
352
|
+
* - `robust_iterations` - Number of robustness iterations performed
|
|
353
|
+
* - `surface` - Surface computation method used
|
|
354
|
+
*
|
|
355
|
+
* # Errors
|
|
356
|
+
*
|
|
357
|
+
* Returns a JSON error object if parsing fails or domain check fails.
|
|
358
|
+
*/
|
|
359
|
+
export function loess_fit(y_json: string, x_vars_json: string, span: number, degree: number, robust_iterations: number, surface: string): string;
|
|
360
|
+
|
|
361
|
+
/**
|
|
362
|
+
* Performs LOESS prediction at new query points via WASM.
|
|
363
|
+
*
|
|
364
|
+
* Predicts LOESS fitted values at arbitrary new points by redoing the
|
|
365
|
+
* local fitting at each query point using the original training data.
|
|
366
|
+
*
|
|
367
|
+
* # Arguments
|
|
368
|
+
*
|
|
369
|
+
* * `new_x_json` - JSON array of new predictor values (p vectors, each of length m)
|
|
370
|
+
* * `original_x_json` - JSON array of original training predictors
|
|
371
|
+
* * `original_y_json` - JSON array of original training response values
|
|
372
|
+
* * `span` - Span parameter (must match the original fit)
|
|
373
|
+
* * `degree` - Degree of polynomial (must match the original fit)
|
|
374
|
+
* * `robust_iterations` - Robustness iterations (must match the original fit)
|
|
375
|
+
* * `surface` - Surface computation method: "direct" or "interpolate"
|
|
376
|
+
*
|
|
377
|
+
* # Returns
|
|
378
|
+
*
|
|
379
|
+
* JSON string containing:
|
|
380
|
+
* - `predictions` - Vector of predicted values at query points
|
|
381
|
+
*
|
|
382
|
+
* # Errors
|
|
383
|
+
*
|
|
384
|
+
* Returns a JSON error object if parsing fails, parameters don't match
|
|
385
|
+
* the original fit, or domain check fails.
|
|
386
|
+
*/
|
|
387
|
+
export function loess_predict(new_x_json: string, original_x_json: string, original_y_json: string, span: number, degree: number, robust_iterations: number, surface: string): string;
|
|
388
|
+
|
|
286
389
|
/**
|
|
287
390
|
* Generates a lambda path for regularized regression via WASM.
|
|
288
391
|
*
|
|
@@ -652,6 +755,35 @@ export function test_r_accuracy(): string;
|
|
|
652
755
|
*/
|
|
653
756
|
export function test_t_critical(df: number, alpha: number): string;
|
|
654
757
|
|
|
758
|
+
/**
|
|
759
|
+
* Performs Variance Inflation Factor (VIF) analysis via WASM.
|
|
760
|
+
*
|
|
761
|
+
* VIF measures how much the variance of regression coefficients is inflated
|
|
762
|
+
* due to multicollinearity among predictor variables. High VIF values indicate
|
|
763
|
+
* that a predictor is highly correlated with other predictors.
|
|
764
|
+
*
|
|
765
|
+
* # Arguments
|
|
766
|
+
*
|
|
767
|
+
* * `y_json` - JSON array of response variable values
|
|
768
|
+
* * `x_vars_json` - JSON array of predictor arrays
|
|
769
|
+
*
|
|
770
|
+
* # Returns
|
|
771
|
+
*
|
|
772
|
+
* JSON string containing the maximum VIF, detailed VIF results for each predictor,
|
|
773
|
+
* interpretation, and guidance.
|
|
774
|
+
*
|
|
775
|
+
* # Interpretation
|
|
776
|
+
*
|
|
777
|
+
* - VIF = 1: No correlation with other predictors
|
|
778
|
+
* - VIF > 5: Moderate multicollinearity (concerning)
|
|
779
|
+
* - VIF > 10: High multicollinearity (severe)
|
|
780
|
+
*
|
|
781
|
+
* # Errors
|
|
782
|
+
*
|
|
783
|
+
* Returns a JSON error object if parsing fails or domain check fails.
|
|
784
|
+
*/
|
|
785
|
+
export function vif_test(y_json: string, x_vars_json: string): string;
|
|
786
|
+
|
|
655
787
|
/**
|
|
656
788
|
* Performs the White test for heteroscedasticity via WASM.
|
|
657
789
|
*
|
|
@@ -683,12 +815,16 @@ export interface InitOutput {
|
|
|
683
815
|
readonly breusch_godfrey_test: (a: number, b: number, c: number, d: number, e: number, f: number, g: number) => [number, number];
|
|
684
816
|
readonly breusch_pagan_test: (a: number, b: number, c: number, d: number) => [number, number];
|
|
685
817
|
readonly cooks_distance_test: (a: number, b: number, c: number, d: number) => [number, number];
|
|
818
|
+
readonly dfbetas_test: (a: number, b: number, c: number, d: number) => [number, number];
|
|
819
|
+
readonly dffits_test: (a: number, b: number, c: number, d: number) => [number, number];
|
|
686
820
|
readonly durbin_watson_test: (a: number, b: number, c: number, d: number) => [number, number];
|
|
687
821
|
readonly elastic_net_regression: (a: number, b: number, c: number, d: number, e: number, f: number, g: number, h: number, i: number, j: number, k: number) => [number, number];
|
|
688
822
|
readonly get_version: () => [number, number];
|
|
689
823
|
readonly harvey_collier_test: (a: number, b: number, c: number, d: number) => [number, number];
|
|
690
824
|
readonly jarque_bera_test: (a: number, b: number, c: number, d: number) => [number, number];
|
|
691
825
|
readonly lasso_regression: (a: number, b: number, c: number, d: number, e: number, f: number, g: number, h: number, i: number, j: number) => [number, number];
|
|
826
|
+
readonly loess_fit: (a: number, b: number, c: number, d: number, e: number, f: number, g: number, h: number, i: number) => [number, number];
|
|
827
|
+
readonly loess_predict: (a: number, b: number, c: number, d: number, e: number, f: number, g: number, h: number, i: number, j: number, k: number) => [number, number];
|
|
692
828
|
readonly make_lambda_path: (a: number, b: number, c: number, d: number, e: number, f: number) => [number, number];
|
|
693
829
|
readonly ols_regression: (a: number, b: number, c: number, d: number, e: number, f: number) => [number, number];
|
|
694
830
|
readonly parse_csv: (a: number, b: number) => [number, number];
|
|
@@ -709,6 +845,7 @@ export interface InitOutput {
|
|
|
709
845
|
readonly test_housing_regression: () => [number, number];
|
|
710
846
|
readonly test_r_accuracy: () => [number, number];
|
|
711
847
|
readonly test_t_critical: (a: number, b: number) => [number, number];
|
|
848
|
+
readonly vif_test: (a: number, b: number, c: number, d: number) => [number, number];
|
|
712
849
|
readonly white_test: (a: number, b: number, c: number, d: number, e: number, f: number) => [number, number];
|
|
713
850
|
readonly get_t_cdf: (a: number, b: number) => number;
|
|
714
851
|
readonly get_t_critical: (a: number, b: number) => number;
|
package/linreg_core.js
CHANGED
|
@@ -170,6 +170,86 @@ export function cooks_distance_test(y_json, x_vars_json) {
|
|
|
170
170
|
}
|
|
171
171
|
}
|
|
172
172
|
|
|
173
|
+
/**
|
|
174
|
+
* Performs DFBETAS analysis via WASM.
|
|
175
|
+
*
|
|
176
|
+
* DFBETAS measures the influence of each observation on each regression coefficient.
|
|
177
|
+
* For each observation and each coefficient, it computes the standardized change
|
|
178
|
+
* in the coefficient when that observation is omitted.
|
|
179
|
+
*
|
|
180
|
+
* # Arguments
|
|
181
|
+
*
|
|
182
|
+
* * `y_json` - JSON array of response variable values
|
|
183
|
+
* * `x_vars_json` - JSON array of predictor arrays
|
|
184
|
+
*
|
|
185
|
+
* # Returns
|
|
186
|
+
*
|
|
187
|
+
* JSON string containing the DFBETAS matrix, threshold, and influential observations.
|
|
188
|
+
*
|
|
189
|
+
* # Errors
|
|
190
|
+
*
|
|
191
|
+
* Returns a JSON error object if parsing fails or domain check fails.
|
|
192
|
+
* @param {string} y_json
|
|
193
|
+
* @param {string} x_vars_json
|
|
194
|
+
* @returns {string}
|
|
195
|
+
*/
|
|
196
|
+
export function dfbetas_test(y_json, x_vars_json) {
|
|
197
|
+
let deferred3_0;
|
|
198
|
+
let deferred3_1;
|
|
199
|
+
try {
|
|
200
|
+
const ptr0 = passStringToWasm0(y_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
201
|
+
const len0 = WASM_VECTOR_LEN;
|
|
202
|
+
const ptr1 = passStringToWasm0(x_vars_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
203
|
+
const len1 = WASM_VECTOR_LEN;
|
|
204
|
+
const ret = wasm.dfbetas_test(ptr0, len0, ptr1, len1);
|
|
205
|
+
deferred3_0 = ret[0];
|
|
206
|
+
deferred3_1 = ret[1];
|
|
207
|
+
return getStringFromWasm0(ret[0], ret[1]);
|
|
208
|
+
} finally {
|
|
209
|
+
wasm.__wbindgen_free(deferred3_0, deferred3_1, 1);
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
|
|
213
|
+
/**
|
|
214
|
+
* Performs DFFITS analysis via WASM.
|
|
215
|
+
*
|
|
216
|
+
* DFFITS measures the influence of each observation on its own fitted value.
|
|
217
|
+
* It is the standardized change in the fitted value when that observation
|
|
218
|
+
* is omitted from the model.
|
|
219
|
+
*
|
|
220
|
+
* # Arguments
|
|
221
|
+
*
|
|
222
|
+
* * `y_json` - JSON array of response variable values
|
|
223
|
+
* * `x_vars_json` - JSON array of predictor arrays
|
|
224
|
+
*
|
|
225
|
+
* # Returns
|
|
226
|
+
*
|
|
227
|
+
* JSON string containing the DFFITS vector, threshold, and influential observations.
|
|
228
|
+
*
|
|
229
|
+
* # Errors
|
|
230
|
+
*
|
|
231
|
+
* Returns a JSON error object if parsing fails or domain check fails.
|
|
232
|
+
* @param {string} y_json
|
|
233
|
+
* @param {string} x_vars_json
|
|
234
|
+
* @returns {string}
|
|
235
|
+
*/
|
|
236
|
+
export function dffits_test(y_json, x_vars_json) {
|
|
237
|
+
let deferred3_0;
|
|
238
|
+
let deferred3_1;
|
|
239
|
+
try {
|
|
240
|
+
const ptr0 = passStringToWasm0(y_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
241
|
+
const len0 = WASM_VECTOR_LEN;
|
|
242
|
+
const ptr1 = passStringToWasm0(x_vars_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
243
|
+
const len1 = WASM_VECTOR_LEN;
|
|
244
|
+
const ret = wasm.dffits_test(ptr0, len0, ptr1, len1);
|
|
245
|
+
deferred3_0 = ret[0];
|
|
246
|
+
deferred3_1 = ret[1];
|
|
247
|
+
return getStringFromWasm0(ret[0], ret[1]);
|
|
248
|
+
} finally {
|
|
249
|
+
wasm.__wbindgen_free(deferred3_0, deferred3_1, 1);
|
|
250
|
+
}
|
|
251
|
+
}
|
|
252
|
+
|
|
173
253
|
/**
|
|
174
254
|
* Performs the Durbin-Watson test for autocorrelation via WASM.
|
|
175
255
|
*
|
|
@@ -492,6 +572,116 @@ export function lasso_regression(y_json, x_vars_json, _variable_names, lambda, s
|
|
|
492
572
|
}
|
|
493
573
|
}
|
|
494
574
|
|
|
575
|
+
/**
|
|
576
|
+
* Performs LOESS regression via WASM.
|
|
577
|
+
*
|
|
578
|
+
* LOESS (Locally Estimated Scatterplot Smoothing) is a non-parametric
|
|
579
|
+
* regression method that fits multiple regressions in local subsets
|
|
580
|
+
* of data to create a smooth curve through the data points.
|
|
581
|
+
*
|
|
582
|
+
* # Arguments
|
|
583
|
+
*
|
|
584
|
+
* * `y_json` - JSON array of response variable values
|
|
585
|
+
* * `x_vars_json` - JSON array of predictor arrays
|
|
586
|
+
* * `span` - Fraction of data used in each local fit (0.0 to 1.0)
|
|
587
|
+
* * `degree` - Degree of local polynomial: 0 (constant), 1 (linear), or 2 (quadratic)
|
|
588
|
+
* * `robust_iterations` - Number of robustness iterations (0 for non-robust fit)
|
|
589
|
+
* * `surface` - Surface computation method: "direct" or "interpolate"
|
|
590
|
+
*
|
|
591
|
+
* # Returns
|
|
592
|
+
*
|
|
593
|
+
* JSON string containing:
|
|
594
|
+
* - `fitted` - Fitted values at each observation point
|
|
595
|
+
* - `span` - Span parameter used
|
|
596
|
+
* - `degree` - Degree of polynomial used
|
|
597
|
+
* - `robust_iterations` - Number of robustness iterations performed
|
|
598
|
+
* - `surface` - Surface computation method used
|
|
599
|
+
*
|
|
600
|
+
* # Errors
|
|
601
|
+
*
|
|
602
|
+
* Returns a JSON error object if parsing fails or domain check fails.
|
|
603
|
+
* @param {string} y_json
|
|
604
|
+
* @param {string} x_vars_json
|
|
605
|
+
* @param {number} span
|
|
606
|
+
* @param {number} degree
|
|
607
|
+
* @param {number} robust_iterations
|
|
608
|
+
* @param {string} surface
|
|
609
|
+
* @returns {string}
|
|
610
|
+
*/
|
|
611
|
+
export function loess_fit(y_json, x_vars_json, span, degree, robust_iterations, surface) {
|
|
612
|
+
let deferred4_0;
|
|
613
|
+
let deferred4_1;
|
|
614
|
+
try {
|
|
615
|
+
const ptr0 = passStringToWasm0(y_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
616
|
+
const len0 = WASM_VECTOR_LEN;
|
|
617
|
+
const ptr1 = passStringToWasm0(x_vars_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
618
|
+
const len1 = WASM_VECTOR_LEN;
|
|
619
|
+
const ptr2 = passStringToWasm0(surface, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
620
|
+
const len2 = WASM_VECTOR_LEN;
|
|
621
|
+
const ret = wasm.loess_fit(ptr0, len0, ptr1, len1, span, degree, robust_iterations, ptr2, len2);
|
|
622
|
+
deferred4_0 = ret[0];
|
|
623
|
+
deferred4_1 = ret[1];
|
|
624
|
+
return getStringFromWasm0(ret[0], ret[1]);
|
|
625
|
+
} finally {
|
|
626
|
+
wasm.__wbindgen_free(deferred4_0, deferred4_1, 1);
|
|
627
|
+
}
|
|
628
|
+
}
|
|
629
|
+
|
|
630
|
+
/**
|
|
631
|
+
* Performs LOESS prediction at new query points via WASM.
|
|
632
|
+
*
|
|
633
|
+
* Predicts LOESS fitted values at arbitrary new points by redoing the
|
|
634
|
+
* local fitting at each query point using the original training data.
|
|
635
|
+
*
|
|
636
|
+
* # Arguments
|
|
637
|
+
*
|
|
638
|
+
* * `new_x_json` - JSON array of new predictor values (p vectors, each of length m)
|
|
639
|
+
* * `original_x_json` - JSON array of original training predictors
|
|
640
|
+
* * `original_y_json` - JSON array of original training response values
|
|
641
|
+
* * `span` - Span parameter (must match the original fit)
|
|
642
|
+
* * `degree` - Degree of polynomial (must match the original fit)
|
|
643
|
+
* * `robust_iterations` - Robustness iterations (must match the original fit)
|
|
644
|
+
* * `surface` - Surface computation method: "direct" or "interpolate"
|
|
645
|
+
*
|
|
646
|
+
* # Returns
|
|
647
|
+
*
|
|
648
|
+
* JSON string containing:
|
|
649
|
+
* - `predictions` - Vector of predicted values at query points
|
|
650
|
+
*
|
|
651
|
+
* # Errors
|
|
652
|
+
*
|
|
653
|
+
* Returns a JSON error object if parsing fails, parameters don't match
|
|
654
|
+
* the original fit, or domain check fails.
|
|
655
|
+
* @param {string} new_x_json
|
|
656
|
+
* @param {string} original_x_json
|
|
657
|
+
* @param {string} original_y_json
|
|
658
|
+
* @param {number} span
|
|
659
|
+
* @param {number} degree
|
|
660
|
+
* @param {number} robust_iterations
|
|
661
|
+
* @param {string} surface
|
|
662
|
+
* @returns {string}
|
|
663
|
+
*/
|
|
664
|
+
export function loess_predict(new_x_json, original_x_json, original_y_json, span, degree, robust_iterations, surface) {
|
|
665
|
+
let deferred5_0;
|
|
666
|
+
let deferred5_1;
|
|
667
|
+
try {
|
|
668
|
+
const ptr0 = passStringToWasm0(new_x_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
669
|
+
const len0 = WASM_VECTOR_LEN;
|
|
670
|
+
const ptr1 = passStringToWasm0(original_x_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
671
|
+
const len1 = WASM_VECTOR_LEN;
|
|
672
|
+
const ptr2 = passStringToWasm0(original_y_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
673
|
+
const len2 = WASM_VECTOR_LEN;
|
|
674
|
+
const ptr3 = passStringToWasm0(surface, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
675
|
+
const len3 = WASM_VECTOR_LEN;
|
|
676
|
+
const ret = wasm.loess_predict(ptr0, len0, ptr1, len1, ptr2, len2, span, degree, robust_iterations, ptr3, len3);
|
|
677
|
+
deferred5_0 = ret[0];
|
|
678
|
+
deferred5_1 = ret[1];
|
|
679
|
+
return getStringFromWasm0(ret[0], ret[1]);
|
|
680
|
+
} finally {
|
|
681
|
+
wasm.__wbindgen_free(deferred5_0, deferred5_1, 1);
|
|
682
|
+
}
|
|
683
|
+
}
|
|
684
|
+
|
|
495
685
|
/**
|
|
496
686
|
* Generates a lambda path for regularized regression via WASM.
|
|
497
687
|
*
|
|
@@ -1200,6 +1390,53 @@ export function test_t_critical(df, alpha) {
|
|
|
1200
1390
|
}
|
|
1201
1391
|
}
|
|
1202
1392
|
|
|
1393
|
+
/**
|
|
1394
|
+
* Performs Variance Inflation Factor (VIF) analysis via WASM.
|
|
1395
|
+
*
|
|
1396
|
+
* VIF measures how much the variance of regression coefficients is inflated
|
|
1397
|
+
* due to multicollinearity among predictor variables. High VIF values indicate
|
|
1398
|
+
* that a predictor is highly correlated with other predictors.
|
|
1399
|
+
*
|
|
1400
|
+
* # Arguments
|
|
1401
|
+
*
|
|
1402
|
+
* * `y_json` - JSON array of response variable values
|
|
1403
|
+
* * `x_vars_json` - JSON array of predictor arrays
|
|
1404
|
+
*
|
|
1405
|
+
* # Returns
|
|
1406
|
+
*
|
|
1407
|
+
* JSON string containing the maximum VIF, detailed VIF results for each predictor,
|
|
1408
|
+
* interpretation, and guidance.
|
|
1409
|
+
*
|
|
1410
|
+
* # Interpretation
|
|
1411
|
+
*
|
|
1412
|
+
* - VIF = 1: No correlation with other predictors
|
|
1413
|
+
* - VIF > 5: Moderate multicollinearity (concerning)
|
|
1414
|
+
* - VIF > 10: High multicollinearity (severe)
|
|
1415
|
+
*
|
|
1416
|
+
* # Errors
|
|
1417
|
+
*
|
|
1418
|
+
* Returns a JSON error object if parsing fails or domain check fails.
|
|
1419
|
+
* @param {string} y_json
|
|
1420
|
+
* @param {string} x_vars_json
|
|
1421
|
+
* @returns {string}
|
|
1422
|
+
*/
|
|
1423
|
+
export function vif_test(y_json, x_vars_json) {
|
|
1424
|
+
let deferred3_0;
|
|
1425
|
+
let deferred3_1;
|
|
1426
|
+
try {
|
|
1427
|
+
const ptr0 = passStringToWasm0(y_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
1428
|
+
const len0 = WASM_VECTOR_LEN;
|
|
1429
|
+
const ptr1 = passStringToWasm0(x_vars_json, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
|
|
1430
|
+
const len1 = WASM_VECTOR_LEN;
|
|
1431
|
+
const ret = wasm.vif_test(ptr0, len0, ptr1, len1);
|
|
1432
|
+
deferred3_0 = ret[0];
|
|
1433
|
+
deferred3_1 = ret[1];
|
|
1434
|
+
return getStringFromWasm0(ret[0], ret[1]);
|
|
1435
|
+
} finally {
|
|
1436
|
+
wasm.__wbindgen_free(deferred3_0, deferred3_1, 1);
|
|
1437
|
+
}
|
|
1438
|
+
}
|
|
1439
|
+
|
|
1203
1440
|
/**
|
|
1204
1441
|
* Performs the White test for heteroscedasticity via WASM.
|
|
1205
1442
|
*
|
package/linreg_core_bg.wasm
CHANGED
|
Binary file
|
package/package.json
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
"Jesse Anderson"
|
|
6
6
|
],
|
|
7
7
|
"description": "Lightweight linear regression (OLS, Ridge, Lasso, Elastic Net) with diagnostic tests. Pure Rust - no external math dependencies.",
|
|
8
|
-
"version": "0.
|
|
8
|
+
"version": "0.5.0",
|
|
9
9
|
"license": "MIT OR Apache-2.0",
|
|
10
10
|
"repository": {
|
|
11
11
|
"type": "git",
|