scm2cpp-lasso 0.11.0__tar.gz → 0.13.0__tar.gz
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.
- {scm2cpp_lasso-0.11.0/src/scm2cpp_lasso.egg-info → scm2cpp_lasso-0.13.0}/PKG-INFO +37 -2
- scm2cpp_lasso-0.11.0/PKG-INFO → scm2cpp_lasso-0.13.0/README.md +35 -18
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/pyproject.toml +3 -3
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/setup.py +31 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/__init__.py +226 -15
- scm2cpp_lasso-0.13.0/src/scm2cpp_lasso/_generated/_loader_accel_cublas.py +140 -0
- scm2cpp_lasso-0.13.0/src/scm2cpp_lasso/_generated/_loader_gpu_cuda.py +294 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/_loader_gramops_blas.py +95 -6
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/_loader_gramops_loops.py +95 -6
- scm2cpp_lasso-0.13.0/src/scm2cpp_lasso/_generated/accel_cublas/accel.cpp +20 -0
- scm2cpp_lasso-0.13.0/src/scm2cpp_lasso/_generated/accel_cublas/accel.hpp +1023 -0
- scm2cpp_lasso-0.13.0/src/scm2cpp_lasso/_generated/accel_cublas/accel_capi.cpp +64 -0
- scm2cpp_lasso-0.13.0/src/scm2cpp_lasso/_generated/gpu_cuda/gpu.cpp +35 -0
- scm2cpp_lasso-0.13.0/src/scm2cpp_lasso/_generated/gpu_cuda/gpu.hpp +3715 -0
- scm2cpp_lasso-0.13.0/src/scm2cpp_lasso/_generated/gpu_cuda/gpu_capi.cpp +289 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/gramops_blas/gramops.cpp +12 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/gramops_blas/gramops.hpp +727 -22
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/gramops_blas/gramops_capi.cpp +38 -2
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/gramops_loops/gramops.cpp +12 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/gramops_loops/gramops.hpp +877 -102
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/gramops_loops/gramops_capi.cpp +38 -2
- scm2cpp_lasso-0.13.0/src/scm2cpp_lasso/_generated/scm2cpp-cuda.hpp +285 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/scm2cpp.hpp +18 -7
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_libfind.py +24 -0
- scm2cpp_lasso-0.11.0/README.md → scm2cpp_lasso-0.13.0/src/scm2cpp_lasso.egg-info/PKG-INFO +53 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso.egg-info/SOURCES.txt +9 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/setup.cfg +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/__init__.py +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/_loader.py +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/_loader_classifiers.py +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/_loader_derived_blas.py +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/_loader_derived_cublas.py +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/_loader_derived_loops.py +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/_loader_nmf_blas.py +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/_loader_nmf_cublas.py +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/_loader_nmf_loops.py +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/classifiers.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/classifiers.hpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/classifiers_capi.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/derived_blas/lasso_design.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/derived_blas/lasso_design.hpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/derived_blas/lasso_design_capi.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/derived_cublas/lasso_design.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/derived_cublas/lasso_design.hpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/derived_cublas/lasso_design_capi.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/derived_loops/lasso_design.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/derived_loops/lasso_design.hpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/derived_loops/lasso_design_capi.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/lasso_cov.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/lasso_cov.hpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/lasso_cov_capi.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/nmf_blas/nmf_cd.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/nmf_blas/nmf_cd.hpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/nmf_blas/nmf_cd_capi.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/nmf_cublas/nmf_cd.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/nmf_cublas/nmf_cd.hpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/nmf_cublas/nmf_cd_capi.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/nmf_loops/nmf_cd.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/nmf_loops/nmf_cd.hpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/nmf_loops/nmf_cd_capi.cpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/scm2cpp-blas.hpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/_generated/scm2cpp-cublas.hpp +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso/batch_capi.cu +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso.egg-info/dependency_links.txt +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso.egg-info/requires.txt +0 -0
- {scm2cpp_lasso-0.11.0 → scm2cpp_lasso-0.13.0}/src/scm2cpp_lasso.egg-info/top_level.txt +0 -0
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: scm2cpp-lasso
|
|
3
|
-
Version: 0.
|
|
4
|
-
Summary: scikit-learn estimators (lasso, elastic net, ridge, ARD, SVM, SVR, logistic regression, GLMs, Huber, Theil-Sen, NMF, Gaussian mixture, FastICA, PCA, graphical lasso, RANSAC, SGD, OMP, LARS) translated from Scheme to C++ by scm2cpp; GPU batch solver included
|
|
3
|
+
Version: 0.13.0
|
|
4
|
+
Summary: scikit-learn estimators (lasso, elastic net, ridge, ARD, SVM, SVR, logistic regression, GLMs, Huber, Theil-Sen, F-score selection, RFE, NMF, Gaussian mixture, FastICA, PCA, graphical lasso, RANSAC, SGD, OMP, LARS) translated from Scheme to C++ by scm2cpp; GPU batch solver and CUDA kernels included
|
|
5
5
|
Author: Hirotaka Niitsuma
|
|
6
6
|
License: MIT
|
|
7
7
|
Project-URL: Homepage, https://github.com/niitsuma/scm2cpp
|
|
@@ -712,6 +712,41 @@ GramLassoLarsCV().fit(X, y).alpha_
|
|
|
712
712
|
Speed, from the repository README's table: the GLMs 1.1-6x, the CV
|
|
713
713
|
estimators 1.6-6.6x, Theil-Sen 1.3-1.8x (its subset drawing dominates).
|
|
714
714
|
|
|
715
|
+
## Feature selection: `f_regression`, `f_classif`, `SelectKBest`, `SelectPercentile`, `GramRFE`
|
|
716
|
+
|
|
717
|
+
scikit-learn's univariate F statistics and its selectors over them,
|
|
718
|
+
and `RFE` around `Ridge` / `LinearRegression`, translated.
|
|
719
|
+
`f_regression` also takes an n x q array of targets: the q results in
|
|
720
|
+
one product, on the device when one answers.
|
|
721
|
+
|
|
722
|
+
```python
|
|
723
|
+
from scm2cpp_lasso import SelectKBest, GramRFE, f_regression
|
|
724
|
+
SelectKBest("f_regression", k=20).fit(X, y).get_support()
|
|
725
|
+
GramRFE(alpha=1.0, n_features_to_select=10).fit(X, y).ranking_
|
|
726
|
+
F, p = f_regression(X, Y) # Y: n x q, every target at once
|
|
727
|
+
```
|
|
728
|
+
|
|
729
|
+
The same scores, ranking and features as scikit-learn. RFE is 80-1,000x
|
|
730
|
+
faster (one Gram and one Cholesky factor, downdated, instead of a refit
|
|
731
|
+
per round), and f_regression over many targets 30-50x. The Gram-route
|
|
732
|
+
estimators (`GramLassoLarsIC`, `GramLarsCV`, `GramLassoLarsCV`,
|
|
733
|
+
`GramLars`, `GramLassoLars`, `CovPCA`) form a large X'X on the device
|
|
734
|
+
when one answers. `SCM2CPP_NO_DEVICE=1` keeps everything on the CPU.
|
|
735
|
+
|
|
736
|
+
## The GPU build
|
|
737
|
+
|
|
738
|
+
Where the CUDA toolkit is at install time, `ParallelFastICA`,
|
|
739
|
+
`EMGaussianMixture`, `LBFGSLogisticRegression`,
|
|
740
|
+
`LBFGSLogisticRegressionCV`, `LBFGSHuberRegressor` and the `LBFGS*`
|
|
741
|
+
GLMs also get the same Scheme translated with `--cuda`
|
|
742
|
+
(`libscm2cpp_gpu.so`). Its loops are CUDA kernels and its products
|
|
743
|
+
cuBLAS, on arrays that stay on the device. The classes take it when a
|
|
744
|
+
device answers and the data has a million entries or more, and give
|
|
745
|
+
the CPU build's iterations and results to the last digits. Measured
|
|
746
|
+
against scikit-learn: 10-22x for the L-BFGS fits, 6.7x FastICA, 3x the
|
|
747
|
+
mixture and LogisticRegressionCV (the repository README's table).
|
|
748
|
+
`SCM2CPP_NO_DEVICE=1` keeps everything on the CPU.
|
|
749
|
+
|
|
715
750
|
## Logistic regression with L1
|
|
716
751
|
|
|
717
752
|
`CovLogistic` solves L1-penalized logistic regression by
|
|
@@ -1,21 +1,3 @@
|
|
|
1
|
-
Metadata-Version: 2.4
|
|
2
|
-
Name: scm2cpp-lasso
|
|
3
|
-
Version: 0.11.0
|
|
4
|
-
Summary: scikit-learn estimators (lasso, elastic net, ridge, ARD, SVM, SVR, logistic regression, GLMs, Huber, Theil-Sen, NMF, Gaussian mixture, FastICA, PCA, graphical lasso, RANSAC, SGD, OMP, LARS) translated from Scheme to C++ by scm2cpp; GPU batch solver included
|
|
5
|
-
Author: Hirotaka Niitsuma
|
|
6
|
-
License: MIT
|
|
7
|
-
Project-URL: Homepage, https://github.com/niitsuma/scm2cpp
|
|
8
|
-
Project-URL: Source, https://github.com/niitsuma/scm2cpp/tree/master/python/scm2cpp-lasso
|
|
9
|
-
Keywords: lasso,elastic-net,ridge,svm,logistic-regression,coordinate-descent,cuda,compiler
|
|
10
|
-
Classifier: License :: OSI Approved :: MIT License
|
|
11
|
-
Classifier: Programming Language :: Python :: 3
|
|
12
|
-
Classifier: Programming Language :: C++
|
|
13
|
-
Classifier: Topic :: Scientific/Engineering :: Mathematics
|
|
14
|
-
Classifier: Intended Audience :: Science/Research
|
|
15
|
-
Requires-Python: >=3.8
|
|
16
|
-
Description-Content-Type: text/markdown
|
|
17
|
-
Requires-Dist: numpy>=1.17
|
|
18
|
-
|
|
19
1
|
# scm2cpp-lasso
|
|
20
2
|
|
|
21
3
|
*[Japanese (README.ja.md)](README.ja.md)*
|
|
@@ -712,6 +694,41 @@ GramLassoLarsCV().fit(X, y).alpha_
|
|
|
712
694
|
Speed, from the repository README's table: the GLMs 1.1-6x, the CV
|
|
713
695
|
estimators 1.6-6.6x, Theil-Sen 1.3-1.8x (its subset drawing dominates).
|
|
714
696
|
|
|
697
|
+
## Feature selection: `f_regression`, `f_classif`, `SelectKBest`, `SelectPercentile`, `GramRFE`
|
|
698
|
+
|
|
699
|
+
scikit-learn's univariate F statistics and its selectors over them,
|
|
700
|
+
and `RFE` around `Ridge` / `LinearRegression`, translated.
|
|
701
|
+
`f_regression` also takes an n x q array of targets: the q results in
|
|
702
|
+
one product, on the device when one answers.
|
|
703
|
+
|
|
704
|
+
```python
|
|
705
|
+
from scm2cpp_lasso import SelectKBest, GramRFE, f_regression
|
|
706
|
+
SelectKBest("f_regression", k=20).fit(X, y).get_support()
|
|
707
|
+
GramRFE(alpha=1.0, n_features_to_select=10).fit(X, y).ranking_
|
|
708
|
+
F, p = f_regression(X, Y) # Y: n x q, every target at once
|
|
709
|
+
```
|
|
710
|
+
|
|
711
|
+
The same scores, ranking and features as scikit-learn. RFE is 80-1,000x
|
|
712
|
+
faster (one Gram and one Cholesky factor, downdated, instead of a refit
|
|
713
|
+
per round), and f_regression over many targets 30-50x. The Gram-route
|
|
714
|
+
estimators (`GramLassoLarsIC`, `GramLarsCV`, `GramLassoLarsCV`,
|
|
715
|
+
`GramLars`, `GramLassoLars`, `CovPCA`) form a large X'X on the device
|
|
716
|
+
when one answers. `SCM2CPP_NO_DEVICE=1` keeps everything on the CPU.
|
|
717
|
+
|
|
718
|
+
## The GPU build
|
|
719
|
+
|
|
720
|
+
Where the CUDA toolkit is at install time, `ParallelFastICA`,
|
|
721
|
+
`EMGaussianMixture`, `LBFGSLogisticRegression`,
|
|
722
|
+
`LBFGSLogisticRegressionCV`, `LBFGSHuberRegressor` and the `LBFGS*`
|
|
723
|
+
GLMs also get the same Scheme translated with `--cuda`
|
|
724
|
+
(`libscm2cpp_gpu.so`). Its loops are CUDA kernels and its products
|
|
725
|
+
cuBLAS, on arrays that stay on the device. The classes take it when a
|
|
726
|
+
device answers and the data has a million entries or more, and give
|
|
727
|
+
the CPU build's iterations and results to the last digits. Measured
|
|
728
|
+
against scikit-learn: 10-22x for the L-BFGS fits, 6.7x FastICA, 3x the
|
|
729
|
+
mixture and LogisticRegressionCV (the repository README's table).
|
|
730
|
+
`SCM2CPP_NO_DEVICE=1` keeps everything on the CPU.
|
|
731
|
+
|
|
715
732
|
## Logistic regression with L1
|
|
716
733
|
|
|
717
734
|
`CovLogistic` solves L1-penalized logistic regression by
|
|
@@ -4,8 +4,8 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "scm2cpp-lasso"
|
|
7
|
-
version = "0.
|
|
8
|
-
description = "scikit-learn estimators (lasso, elastic net, ridge, ARD, SVM, SVR, logistic regression, GLMs, Huber, Theil-Sen, NMF, Gaussian mixture, FastICA, PCA, graphical lasso, RANSAC, SGD, OMP, LARS) translated from Scheme to C++ by scm2cpp; GPU batch solver included"
|
|
7
|
+
version = "0.13.0"
|
|
8
|
+
description = "scikit-learn estimators (lasso, elastic net, ridge, ARD, SVM, SVR, logistic regression, GLMs, Huber, Theil-Sen, F-score selection, RFE, NMF, Gaussian mixture, FastICA, PCA, graphical lasso, RANSAC, SGD, OMP, LARS) translated from Scheme to C++ by scm2cpp; GPU batch solver and CUDA kernels included"
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
requires-python = ">=3.8"
|
|
11
11
|
license = {text = "MIT"}
|
|
@@ -31,4 +31,4 @@ package-dir = {"" = "src"}
|
|
|
31
31
|
where = ["src"]
|
|
32
32
|
|
|
33
33
|
[tool.setuptools.package-data]
|
|
34
|
-
scm2cpp_lasso = ["_generated/*.hpp", "_generated/*.cpp", "_generated/derived_*/*.hpp", "_generated/derived_*/*.cpp", "_generated/nmf_*/*.hpp", "_generated/nmf_*/*.cpp", "_generated/gramops_*/*.hpp", "_generated/gramops_*/*.cpp", "*.cu"]
|
|
34
|
+
scm2cpp_lasso = ["_generated/*.hpp", "_generated/*.cpp", "_generated/derived_*/*.hpp", "_generated/derived_*/*.cpp", "_generated/nmf_*/*.hpp", "_generated/nmf_*/*.cpp", "_generated/gramops_*/*.hpp", "_generated/gramops_*/*.cpp", "_generated/accel_*/*.hpp", "_generated/accel_*/*.cpp", "_generated/gpu_*/*.hpp", "_generated/gpu_*/*.cpp", "*.cu"]
|
|
@@ -120,6 +120,28 @@ class BuildWithCuda(build_ext):
|
|
|
120
120
|
except (subprocess.CalledProcessError, OSError) as exc:
|
|
121
121
|
print(f"scm2cpp_lasso: no CUDA batch path ({exc}); "
|
|
122
122
|
"the CPU solver is unaffected", file=sys.stderr)
|
|
123
|
+
# the --cuda translation (kernels + device-resident cuBLAS):
|
|
124
|
+
# FastICA, the mixture, the L-BFGS fits
|
|
125
|
+
gpu = GEN / "gpu_cuda" / "gpu_capi.cpp"
|
|
126
|
+
if gpu.exists():
|
|
127
|
+
out2 = Path(self.build_lib) / "scm2cpp_lasso" / "libscm2cpp_gpu.so"
|
|
128
|
+
# the installed device's architecture when one answers
|
|
129
|
+
arch = []
|
|
130
|
+
try:
|
|
131
|
+
if subprocess.run(["nvidia-smi"], capture_output=True).returncode == 0:
|
|
132
|
+
arch = ["-arch=native"]
|
|
133
|
+
except OSError:
|
|
134
|
+
pass
|
|
135
|
+
cmd2 = [nvcc, "-O3", "-std=c++17", "-shared", "-x", "cu", *arch,
|
|
136
|
+
"-Xcompiler", "-fPIC", "-I", str(GEN / "gpu_cuda"), "-I", str(GEN),
|
|
137
|
+
str(gpu), "-o", str(out2), "-lcublas",
|
|
138
|
+
"-Wno-deprecated-gpu-targets", "-diag-suppress", "174,177,550"]
|
|
139
|
+
try:
|
|
140
|
+
subprocess.run(cmd2, check=True)
|
|
141
|
+
print("scm2cpp_lasso: built the --cuda estimators")
|
|
142
|
+
except (subprocess.CalledProcessError, OSError) as exc:
|
|
143
|
+
print(f"scm2cpp_lasso: no --cuda estimators ({exc}); "
|
|
144
|
+
"the CPU paths are unaffected", file=sys.stderr)
|
|
123
145
|
|
|
124
146
|
|
|
125
147
|
# The cuBLAS variant of the derived kernel: host C++ against the CUDA
|
|
@@ -211,4 +233,13 @@ if _cuda is not None:
|
|
|
211
233
|
extra_compile_args=CXXFLAGS + ["-O3", "-fstrict-overflow"],
|
|
212
234
|
))
|
|
213
235
|
|
|
236
|
+
extensions.append(Extension(
|
|
237
|
+
"scm2cpp_lasso._accel_cublas",
|
|
238
|
+
sources=[GEN_REL + "/accel_cublas/accel_capi.cpp"],
|
|
239
|
+
include_dirs=[GEN_REL + "/accel_cublas", GEN_REL, str(_cuda / "include")],
|
|
240
|
+
library_dirs=[str(_cuda / "lib64"), str(_cuda / "lib")],
|
|
241
|
+
libraries=["cublas", "cudart"],
|
|
242
|
+
extra_compile_args=CXXFLAGS + ["-O3", "-fstrict-overflow"],
|
|
243
|
+
))
|
|
244
|
+
|
|
214
245
|
setup(ext_modules=extensions, cmdclass={"build_ext": BuildWithCuda})
|
|
@@ -47,10 +47,11 @@ __all__ = ["CovLasso", "CovRidge", "CovBayesianRidge", "CovLogistic", "CovGroupL
|
|
|
47
47
|
"LBFGSPoissonRegressor", "LBFGSGammaRegressor", "LBFGSTweedieRegressor",
|
|
48
48
|
"GramLarsCV", "GramLassoLarsCV", "GramOMPCV",
|
|
49
49
|
"EMGaussianMixture", "CovPCA", "ParallelFastICA", "CovARDRegression",
|
|
50
|
-
"L1LinearSVM", "WeiszfeldTheilSen",
|
|
50
|
+
"L1LinearSVM", "WeiszfeldTheilSen", "f_regression", "f_classif", "SelectKBest",
|
|
51
|
+
"SelectPercentile", "GramRFE",
|
|
51
52
|
"CovMultiTaskLasso", "CovMultiTaskLassoCV", "DerivedLasso",
|
|
52
53
|
"cuda_available", "derived_backend", "kernel"]
|
|
53
|
-
__version__ = "0.
|
|
54
|
+
__version__ = "0.13.0"
|
|
54
55
|
|
|
55
56
|
_BATCH = load_batch_lib()
|
|
56
57
|
_DP = ctypes.POINTER(ctypes.c_double)
|
|
@@ -1349,7 +1350,7 @@ class LBFGSLogisticRegression:
|
|
|
1349
1350
|
k = nc if multi else 1
|
|
1350
1351
|
coef = np.zeros(k * (p + 1))
|
|
1351
1352
|
out = np.zeros(2)
|
|
1352
|
-
it =
|
|
1353
|
+
it = _gpu_or_cpu(n * p, getattr(self, "backend", None)).logistic_lbfgs(
|
|
1353
1354
|
X, yi.astype(np.float64), coef, out, float(self.C), int(self.max_iter),
|
|
1354
1355
|
float(self.tol), multi, 1 if self.fit_intercept else 0, n, p, k)
|
|
1355
1356
|
self.coef_ = coef[:k * p].reshape(k, p).copy()
|
|
@@ -1417,7 +1418,7 @@ class _LBFGSGLM:
|
|
|
1417
1418
|
coef = np.zeros(p + 1)
|
|
1418
1419
|
out = np.zeros(2)
|
|
1419
1420
|
fam, power = self._family_power()
|
|
1420
|
-
it =
|
|
1421
|
+
it = _gpu_or_cpu(n * p, getattr(self, "backend", None)).glm(X, y, coef, out, fam, float(power), float(self.alpha),
|
|
1421
1422
|
int(self.max_iter), float(self.tol),
|
|
1422
1423
|
1 if self.fit_intercept else 0, n, p)
|
|
1423
1424
|
self.coef_, self.intercept_ = coef[:p].copy(), float(coef[p])
|
|
@@ -1498,7 +1499,7 @@ class LBFGSLogisticRegressionCV:
|
|
|
1498
1499
|
|
|
1499
1500
|
def _path(self, X, yi, Cs, coef, multi, k):
|
|
1500
1501
|
n, p = X.shape
|
|
1501
|
-
lib =
|
|
1502
|
+
lib = _gpu_or_cpu(n * p, getattr(self, "backend", None))
|
|
1502
1503
|
coefs, iters = [], []
|
|
1503
1504
|
out = np.zeros(2)
|
|
1504
1505
|
for C in Cs:
|
|
@@ -1581,7 +1582,7 @@ class LBFGSHuberRegressor:
|
|
|
1581
1582
|
coef = np.zeros(p + 2)
|
|
1582
1583
|
coef[-1] = 1.0
|
|
1583
1584
|
out = np.zeros(2)
|
|
1584
|
-
it =
|
|
1585
|
+
it = _gpu_or_cpu(n * p, getattr(self, "backend", None)).huber(
|
|
1585
1586
|
X, y, coef, out, float(self.epsilon), float(self.alpha), int(self.max_iter),
|
|
1586
1587
|
float(self.tol), 1 if self.fit_intercept else 0, n, p)
|
|
1587
1588
|
self.coef_ = coef[:p].copy()
|
|
@@ -1642,7 +1643,7 @@ class EMGaussianMixture:
|
|
|
1642
1643
|
self.precisions_cholesky_ = np.zeros((k, p, p))
|
|
1643
1644
|
labels = np.zeros(n)
|
|
1644
1645
|
out = np.zeros(2)
|
|
1645
|
-
it =
|
|
1646
|
+
it = _gpu_or_cpu(n * p, getattr(self, "backend", None)).gmm(X, resp, self.weights_, self.means_,
|
|
1646
1647
|
self.precisions_cholesky_, labels, out,
|
|
1647
1648
|
int(self.max_iter), float(self.tol),
|
|
1648
1649
|
float(self.reg_covar), n, p, k)
|
|
@@ -1689,14 +1690,15 @@ class CovPCA:
|
|
|
1689
1690
|
n_components_.
|
|
1690
1691
|
"""
|
|
1691
1692
|
|
|
1692
|
-
def __init__(self, n_components=None):
|
|
1693
|
-
self.n_components = n_components
|
|
1693
|
+
def __init__(self, n_components=None, *, backend=None):
|
|
1694
|
+
self.n_components, self.backend = n_components, backend
|
|
1694
1695
|
|
|
1695
1696
|
def fit(self, X, y=None):
|
|
1696
1697
|
X = np.ascontiguousarray(X, dtype=np.float64)
|
|
1697
1698
|
n, p = X.shape
|
|
1698
1699
|
comps = np.zeros((p, p)); ev = np.zeros(p); sv = np.zeros(p); mean = np.zeros(p)
|
|
1699
|
-
|
|
1700
|
+
lib = _accel(float(n) * p * p) if self.backend in (None, "cublas") else None
|
|
1701
|
+
(lib or _gramops_kernels()).pca(X, comps, ev, sv, mean, n, p)
|
|
1700
1702
|
k = min(n, p) if self.n_components is None else int(self.n_components)
|
|
1701
1703
|
self.n_components_ = k
|
|
1702
1704
|
self.mean_ = mean
|
|
@@ -1742,7 +1744,7 @@ class ParallelFastICA:
|
|
|
1742
1744
|
w0 = np.ascontiguousarray(w0)
|
|
1743
1745
|
self.components_ = np.zeros((k, p)); self.whitening_ = np.zeros((k, p))
|
|
1744
1746
|
self._unmixing = np.zeros((k, k)); self.mean_ = np.zeros(p)
|
|
1745
|
-
self.n_iter_ =
|
|
1747
|
+
self.n_iter_ = _gpu_or_cpu(n * p, getattr(self, "backend", None)).fastica(
|
|
1746
1748
|
X, w0, self.components_, self.whitening_, self._unmixing, self.mean_,
|
|
1747
1749
|
int(self.max_iter), float(self.tol), n, p, k)
|
|
1748
1750
|
self.mixing_ = np.linalg.pinv(self.components_)
|
|
@@ -1801,11 +1803,220 @@ class CovARDRegression:
|
|
|
1801
1803
|
return np.ascontiguousarray(X, dtype=np.float64) @ self.coef_ + self.intercept_
|
|
1802
1804
|
|
|
1803
1805
|
|
|
1806
|
+
def _gpu_or_cpu(size, backend=None):
|
|
1807
|
+
"""The --cuda translation (kernels and device-resident cuBLAS) when it
|
|
1808
|
+
was built, a device answers, the backend allows it and the problem has
|
|
1809
|
+
at least a million entries; the CPU library otherwise."""
|
|
1810
|
+
import os
|
|
1811
|
+
from ._libfind import gpu_built
|
|
1812
|
+
if (backend in (None, "cuda") and size >= 1e6 and not os.environ.get("SCM2CPP_NO_DEVICE")
|
|
1813
|
+
and gpu_built() and cuda_available()):
|
|
1814
|
+
import importlib
|
|
1815
|
+
return importlib.import_module(f"{__name__}._generated._loader_gpu_cuda")
|
|
1816
|
+
return _gramops_kernels()
|
|
1817
|
+
|
|
1818
|
+
|
|
1819
|
+
def _accel(work):
|
|
1820
|
+
"""The --cublas build of the selection and Gram products, when it was
|
|
1821
|
+
built, a device answers, and WORK (flops) is large enough to pay for
|
|
1822
|
+
the transfer; else None."""
|
|
1823
|
+
import os
|
|
1824
|
+
from ._libfind import accel_built
|
|
1825
|
+
if (work < 2e9 or os.environ.get("SCM2CPP_NO_DEVICE") or not accel_built()
|
|
1826
|
+
or not cuda_available()):
|
|
1827
|
+
return None
|
|
1828
|
+
import importlib
|
|
1829
|
+
return importlib.import_module(f"{__name__}._generated._loader_accel_cublas")
|
|
1830
|
+
|
|
1831
|
+
|
|
1832
|
+
def _gram(Xc, backend=None):
|
|
1833
|
+
"""X'X: on the device for a large product when one answers, else numpy."""
|
|
1834
|
+
n, p = Xc.shape
|
|
1835
|
+
lib = _accel(float(n) * p * p) if backend in (None, "cublas") else None
|
|
1836
|
+
if lib is None:
|
|
1837
|
+
return np.ascontiguousarray(Xc.T @ Xc)
|
|
1838
|
+
G = np.zeros((p, p))
|
|
1839
|
+
lib.gram_xx(np.ascontiguousarray(Xc), G, n, p)
|
|
1840
|
+
return G
|
|
1841
|
+
|
|
1842
|
+
|
|
1843
|
+
def _cpu_select_lib():
|
|
1844
|
+
return _gramops_kernels()
|
|
1845
|
+
|
|
1846
|
+
|
|
1847
|
+
def f_regression(X, y, *, center=True, backend=None):
|
|
1848
|
+
"""scikit-learn's ``f_regression`` translated (``fscore.scm``): F and
|
|
1849
|
+
p-values of each feature against y. ``y`` may also be n x q, the q
|
|
1850
|
+
targets in one call (one product X'Y, on the device when one answers
|
|
1851
|
+
and the product is large) -- what a loop of scikit-learn's calls
|
|
1852
|
+
gives, column by column. Infinite F (perfect correlation) becomes
|
|
1853
|
+
the largest double and NaN F zero with p-value 1, as
|
|
1854
|
+
force_finite=True has it. p-values need scipy (else None)."""
|
|
1855
|
+
X = np.ascontiguousarray(X, dtype=np.float64)
|
|
1856
|
+
Y = np.asarray(y, dtype=np.float64)
|
|
1857
|
+
one = Y.ndim == 1
|
|
1858
|
+
Y = np.ascontiguousarray(Y.reshape(len(Y), -1))
|
|
1859
|
+
n, p = X.shape
|
|
1860
|
+
q = Y.shape[1]
|
|
1861
|
+
lib = _accel(float(n) * p * q) if backend in (None, "cublas") else None
|
|
1862
|
+
if lib is None:
|
|
1863
|
+
lib = _cpu_select_lib()
|
|
1864
|
+
r = np.zeros((p, q))
|
|
1865
|
+
F = np.zeros((p, q))
|
|
1866
|
+
with np.errstate(divide="ignore", invalid="ignore"):
|
|
1867
|
+
lib.f_regression(X, Y, r, F, 1 if center else 0, n, p, q)
|
|
1868
|
+
dof = n - (2 if center else 1)
|
|
1869
|
+
try:
|
|
1870
|
+
from scipy import stats
|
|
1871
|
+
pv = stats.f.sf(F, 1, dof)
|
|
1872
|
+
except ImportError:
|
|
1873
|
+
pv = None
|
|
1874
|
+
inf = np.isinf(F)
|
|
1875
|
+
F[inf] = np.finfo(np.float64).max
|
|
1876
|
+
nan = np.isnan(F)
|
|
1877
|
+
F[nan] = 0.0
|
|
1878
|
+
if pv is not None:
|
|
1879
|
+
pv[nan] = 1.0
|
|
1880
|
+
if one:
|
|
1881
|
+
return F[:, 0], (None if pv is None else pv[:, 0])
|
|
1882
|
+
return F, pv
|
|
1883
|
+
|
|
1884
|
+
|
|
1885
|
+
def f_classif(X, y):
|
|
1886
|
+
"""scikit-learn's ``f_classif`` translated (``fscore.scm``: f_oneway's
|
|
1887
|
+
sums of squares, the class sums one product). p-values need scipy."""
|
|
1888
|
+
X = np.ascontiguousarray(X, dtype=np.float64)
|
|
1889
|
+
classes, lab = np.unique(np.asarray(y), return_inverse=True)
|
|
1890
|
+
n, p = X.shape
|
|
1891
|
+
k = len(classes)
|
|
1892
|
+
F = np.zeros(p)
|
|
1893
|
+
with np.errstate(divide="ignore", invalid="ignore"):
|
|
1894
|
+
_cpu_select_lib().f_classif(X, lab.astype(np.int32), F, n, p, k)
|
|
1895
|
+
try:
|
|
1896
|
+
from scipy import special
|
|
1897
|
+
pv = special.fdtrc(k - 1, n - k, F)
|
|
1898
|
+
except ImportError:
|
|
1899
|
+
pv = None
|
|
1900
|
+
return F, pv
|
|
1901
|
+
|
|
1902
|
+
|
|
1903
|
+
def _clean_nans(scores):
|
|
1904
|
+
scores = np.array(scores, dtype=np.float64, copy=True)
|
|
1905
|
+
scores[np.isnan(scores)] = np.finfo(np.float64).min
|
|
1906
|
+
return scores
|
|
1907
|
+
|
|
1908
|
+
|
|
1909
|
+
class _SelectBase:
|
|
1910
|
+
def fit(self, X, y):
|
|
1911
|
+
sf = self.score_func
|
|
1912
|
+
fn = {"f_classif": f_classif, "f_regression": f_regression}.get(sf, sf)
|
|
1913
|
+
self.scores_, self.pvalues_ = fn(X, y)
|
|
1914
|
+
return self
|
|
1915
|
+
|
|
1916
|
+
def transform(self, X):
|
|
1917
|
+
return np.asarray(X)[:, self.get_support()]
|
|
1918
|
+
|
|
1919
|
+
def fit_transform(self, X, y):
|
|
1920
|
+
return self.fit(X, y).transform(X)
|
|
1921
|
+
|
|
1922
|
+
|
|
1923
|
+
class SelectKBest(_SelectBase):
|
|
1924
|
+
"""scikit-learn's ``SelectKBest`` over the translated F statistics
|
|
1925
|
+
(``score_func`` "f_classif", "f_regression", or one of this module's
|
|
1926
|
+
functions): the k best scores by a stable sort, NaN scores last.
|
|
1927
|
+
|
|
1928
|
+
Attributes after fit: scores_, pvalues_.
|
|
1929
|
+
"""
|
|
1930
|
+
|
|
1931
|
+
def __init__(self, score_func="f_classif", *, k=10):
|
|
1932
|
+
self.score_func, self.k = score_func, k
|
|
1933
|
+
|
|
1934
|
+
def get_support(self):
|
|
1935
|
+
if self.k == "all":
|
|
1936
|
+
return np.ones(len(self.scores_), dtype=bool)
|
|
1937
|
+
mask = np.zeros(len(self.scores_), dtype=bool)
|
|
1938
|
+
if self.k == 0:
|
|
1939
|
+
return mask
|
|
1940
|
+
mask[np.argsort(_clean_nans(self.scores_), kind="mergesort")[-self.k:]] = True
|
|
1941
|
+
return mask
|
|
1942
|
+
|
|
1943
|
+
|
|
1944
|
+
class SelectPercentile(_SelectBase):
|
|
1945
|
+
"""scikit-learn's ``SelectPercentile`` over the translated F
|
|
1946
|
+
statistics: scores above the (100 - percentile)th percentile, ties
|
|
1947
|
+
at it kept in order up to the percentile's count.
|
|
1948
|
+
|
|
1949
|
+
Attributes after fit: scores_, pvalues_.
|
|
1950
|
+
"""
|
|
1951
|
+
|
|
1952
|
+
def __init__(self, score_func="f_classif", *, percentile=10):
|
|
1953
|
+
self.score_func, self.percentile = score_func, percentile
|
|
1954
|
+
|
|
1955
|
+
def get_support(self):
|
|
1956
|
+
if self.percentile == 100:
|
|
1957
|
+
return np.ones(len(self.scores_), dtype=bool)
|
|
1958
|
+
if self.percentile == 0:
|
|
1959
|
+
return np.zeros(len(self.scores_), dtype=bool)
|
|
1960
|
+
scores = _clean_nans(self.scores_)
|
|
1961
|
+
threshold = np.percentile(scores, 100 - self.percentile)
|
|
1962
|
+
mask = scores > threshold
|
|
1963
|
+
ties = np.where(scores == threshold)[0]
|
|
1964
|
+
if len(ties):
|
|
1965
|
+
max_feats = int(len(scores) * self.percentile / 100)
|
|
1966
|
+
mask[ties[: max_feats - mask.sum()]] = True
|
|
1967
|
+
return mask
|
|
1968
|
+
|
|
1969
|
+
|
|
1970
|
+
class GramRFE:
|
|
1971
|
+
"""scikit-learn's ``RFE`` around ``Ridge(alpha)`` (``alpha=0``:
|
|
1972
|
+
``LinearRegression()``) translated whole (``rfe.scm``): the centred
|
|
1973
|
+
Gram formed once (on the device for a large one when one answers),
|
|
1974
|
+
each round's fit from its Cholesky factor with the dropped features
|
|
1975
|
+
taken out by plane rotations, the features ranked by coef^2 in a
|
|
1976
|
+
stable order. scikit-learn refits from X every round; the ranking
|
|
1977
|
+
and the final coefficients are the same to rounding.
|
|
1978
|
+
|
|
1979
|
+
Attributes after fit: support_, ranking_, n_features_, coef_,
|
|
1980
|
+
intercept_.
|
|
1981
|
+
"""
|
|
1982
|
+
|
|
1983
|
+
def __init__(self, alpha=1.0, *, n_features_to_select=None, step=1, backend=None):
|
|
1984
|
+
self.alpha, self.n_features_to_select, self.step = alpha, n_features_to_select, step
|
|
1985
|
+
self.backend = backend
|
|
1986
|
+
|
|
1987
|
+
def fit(self, X, y):
|
|
1988
|
+
X = np.ascontiguousarray(X, dtype=np.float64)
|
|
1989
|
+
y = np.ascontiguousarray(y, dtype=np.float64)
|
|
1990
|
+
n, p = X.shape
|
|
1991
|
+
k = self.n_features_to_select
|
|
1992
|
+
nsel = p // 2 if k is None else (int(k) if isinstance(k, (int, np.integer)) else int(p * k))
|
|
1993
|
+
step = int(max(1, self.step * p)) if 0.0 < self.step < 1.0 else int(self.step)
|
|
1994
|
+
lib = _accel(float(n) * p * p) if self.backend in (None, "cublas") else None
|
|
1995
|
+
if lib is None:
|
|
1996
|
+
lib = _cpu_select_lib()
|
|
1997
|
+
coef = np.zeros(p)
|
|
1998
|
+
support = np.zeros(p, dtype=np.int32)
|
|
1999
|
+
ranking = np.zeros(p, dtype=np.int32)
|
|
2000
|
+
lib.rfe(X, y, coef, support, ranking, float(self.alpha), nsel, step, n, p)
|
|
2001
|
+
self.support_ = support.astype(bool)
|
|
2002
|
+
self.ranking_ = ranking.astype(int)
|
|
2003
|
+
self.n_features_ = int(self.support_.sum())
|
|
2004
|
+
self.coef_ = coef[self.support_].copy()
|
|
2005
|
+
self.intercept_ = float(y.mean() - X.mean(axis=0)[self.support_] @ self.coef_)
|
|
2006
|
+
return self
|
|
2007
|
+
|
|
2008
|
+
def transform(self, X):
|
|
2009
|
+
return np.asarray(X)[:, self.support_]
|
|
2010
|
+
|
|
2011
|
+
def predict(self, X):
|
|
2012
|
+
return self.transform(np.asarray(X, dtype=np.float64)) @ self.coef_ + self.intercept_
|
|
2013
|
+
|
|
2014
|
+
|
|
1804
2015
|
class _GramLarsBase:
|
|
1805
2016
|
def _fit_lars(self, X, y, method, alpha, max_iter):
|
|
1806
2017
|
Xc, yc, xm, ym = _center(X, y, self.fit_intercept)
|
|
1807
2018
|
n, p = Xc.shape
|
|
1808
|
-
G =
|
|
2019
|
+
G = _gram(Xc)
|
|
1809
2020
|
cov = Xc.T @ yc
|
|
1810
2021
|
self.coef_ = np.zeros(p)
|
|
1811
2022
|
self.n_iter_ = _classifier_kernels().lars(
|
|
@@ -1868,7 +2079,7 @@ class _GramLarsCVBase:
|
|
|
1868
2079
|
|
|
1869
2080
|
def _lars(self, Xc, yc, alpha_min, rec):
|
|
1870
2081
|
n, p = Xc.shape
|
|
1871
|
-
G =
|
|
2082
|
+
G = _gram(Xc)
|
|
1872
2083
|
cov = Xc.T @ yc
|
|
1873
2084
|
coef = np.zeros(p)
|
|
1874
2085
|
path = np.zeros((self.max_iter + 1, p)) if rec else np.zeros(1)
|
|
@@ -1889,7 +2100,7 @@ class _GramLarsCVBase:
|
|
|
1889
2100
|
xm, ym = Xtr.mean(axis=0), ytr.mean()
|
|
1890
2101
|
Xtr, Xte, ytr, yte = Xtr - xm, Xte - xm, ytr - ym, yte - ym
|
|
1891
2102
|
_, _, path, alphas = self._lars(np.ascontiguousarray(Xtr), ytr, 0.0, True)
|
|
1892
|
-
folds.append((alphas, path, Xte
|
|
2103
|
+
folds.append((alphas, path, _gram(Xte), Xte.T @ yte, float(yte @ yte), len(test)))
|
|
1893
2104
|
all_alphas = np.unique(np.concatenate([f[0] for f in folds]))
|
|
1894
2105
|
stride = int(max(1, int(len(all_alphas) / float(self.max_n_alphas))))
|
|
1895
2106
|
all_alphas = all_alphas[::stride]
|
|
@@ -1998,7 +2209,7 @@ class GramLassoLarsIC:
|
|
|
1998
2209
|
def fit(self, X, y):
|
|
1999
2210
|
Xc, yc, xm, ym = _center(X, y, self.fit_intercept)
|
|
2000
2211
|
n, p = Xc.shape
|
|
2001
|
-
G0 =
|
|
2212
|
+
G0 = _gram(Xc)
|
|
2002
2213
|
cov0 = Xc.T @ yc
|
|
2003
2214
|
yy = float(yc @ yc)
|
|
2004
2215
|
path = np.zeros((self.max_iter + 1, p))
|
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
# ctypes loader for libaccel.so, generated alongside it.
|
|
2
|
+
# Arrays are numpy arrays of the declared dtype; they are made
|
|
3
|
+
# contiguous on the way in and mutated in place where the translated
|
|
4
|
+
# function mutates them.
|
|
5
|
+
import ctypes
|
|
6
|
+
import numpy as np
|
|
7
|
+
from pathlib import Path
|
|
8
|
+
|
|
9
|
+
from .._libfind import load_accel_lib as _load_accel_lib
|
|
10
|
+
|
|
11
|
+
_lib = _load_accel_lib()
|
|
12
|
+
|
|
13
|
+
_lib.scm2cpp_f_regression.restype = ctypes.c_int
|
|
14
|
+
_lib.scm2cpp_f_regression.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.c_int, ctypes.c_int, ctypes.c_int, ctypes.c_int]
|
|
15
|
+
def f_regression(x, y, r, f, center, n, p, q):
|
|
16
|
+
x = np.ascontiguousarray(x, dtype=np.float64)
|
|
17
|
+
y = np.ascontiguousarray(y, dtype=np.float64)
|
|
18
|
+
r = np.ascontiguousarray(r, dtype=np.float64)
|
|
19
|
+
f = np.ascontiguousarray(f, dtype=np.float64)
|
|
20
|
+
return _lib.scm2cpp_f_regression(x.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), y.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), r.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), f.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), center, n, p, q)
|
|
21
|
+
|
|
22
|
+
_lib.scm2cpp_f_classif.restype = ctypes.c_int
|
|
23
|
+
_lib.scm2cpp_f_classif.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_int), ctypes.POINTER(ctypes.c_double), ctypes.c_int, ctypes.c_int, ctypes.c_int]
|
|
24
|
+
def f_classif(x, lab, f, n, p, k):
|
|
25
|
+
x = np.ascontiguousarray(x, dtype=np.float64)
|
|
26
|
+
lab = np.ascontiguousarray(lab, dtype=np.int32)
|
|
27
|
+
f = np.ascontiguousarray(f, dtype=np.float64)
|
|
28
|
+
return _lib.scm2cpp_f_classif(x.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), lab.ctypes.data_as(ctypes.POINTER(ctypes.c_int)), f.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), n, p, k)
|
|
29
|
+
|
|
30
|
+
_lib.scm2cpp_min_pos.restype = ctypes.c_double
|
|
31
|
+
_lib.scm2cpp_min_pos.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.c_int]
|
|
32
|
+
def min_pos(v, m):
|
|
33
|
+
v = np.ascontiguousarray(v, dtype=np.float64)
|
|
34
|
+
return _lib.scm2cpp_min_pos(v.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), m)
|
|
35
|
+
|
|
36
|
+
_lib.scm2cpp_round_even.restype = ctypes.c_double
|
|
37
|
+
_lib.scm2cpp_round_even.argtypes = [ctypes.c_double]
|
|
38
|
+
def round_even(y):
|
|
39
|
+
return _lib.scm2cpp_round_even(y)
|
|
40
|
+
|
|
41
|
+
_lib.scm2cpp_cholesky_delete.restype = ctypes.c_int
|
|
42
|
+
_lib.scm2cpp_cholesky_delete.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.c_int, ctypes.c_int, ctypes.c_int]
|
|
43
|
+
def cholesky_delete(l, go, n, k):
|
|
44
|
+
l = np.ascontiguousarray(l, dtype=np.float64)
|
|
45
|
+
return _lib.scm2cpp_cholesky_delete(l.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), go, n, k)
|
|
46
|
+
|
|
47
|
+
_lib.scm2cpp_swap_rc.restype = ctypes.c_int
|
|
48
|
+
_lib.scm2cpp_swap_rc.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.c_int, ctypes.c_int, ctypes.c_int]
|
|
49
|
+
def swap_rc(g, a, b, p):
|
|
50
|
+
g = np.ascontiguousarray(g, dtype=np.float64)
|
|
51
|
+
return _lib.scm2cpp_swap_rc(g.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), a, b, p)
|
|
52
|
+
|
|
53
|
+
_lib.scm2cpp_lars.restype = ctypes.c_int
|
|
54
|
+
_lib.scm2cpp_lars.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.c_int, ctypes.c_double, ctypes.c_double, ctypes.c_int, ctypes.c_int, ctypes.c_double, ctypes.c_int]
|
|
55
|
+
def lars(g, cov, coef, path, alphas, rec, nsamples, alphamin, method, maxiter, eps, p):
|
|
56
|
+
g = np.ascontiguousarray(g, dtype=np.float64)
|
|
57
|
+
cov = np.ascontiguousarray(cov, dtype=np.float64)
|
|
58
|
+
coef = np.ascontiguousarray(coef, dtype=np.float64)
|
|
59
|
+
path = np.ascontiguousarray(path, dtype=np.float64)
|
|
60
|
+
alphas = np.ascontiguousarray(alphas, dtype=np.float64)
|
|
61
|
+
return _lib.scm2cpp_lars(g.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), cov.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), coef.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), path.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), alphas.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), rec, nsamples, alphamin, method, maxiter, eps, p)
|
|
62
|
+
|
|
63
|
+
_lib.scm2cpp_rfe_chol.restype = ctypes.c_int
|
|
64
|
+
_lib.scm2cpp_rfe_chol.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_int), ctypes.POINTER(ctypes.c_double), ctypes.c_double, ctypes.c_int, ctypes.c_int]
|
|
65
|
+
def rfe_chol(g, idx, l, alpha, k, p):
|
|
66
|
+
g = np.ascontiguousarray(g, dtype=np.float64)
|
|
67
|
+
idx = np.ascontiguousarray(idx, dtype=np.int32)
|
|
68
|
+
l = np.ascontiguousarray(l, dtype=np.float64)
|
|
69
|
+
return _lib.scm2cpp_rfe_chol(g.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), idx.ctypes.data_as(ctypes.POINTER(ctypes.c_int)), l.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), alpha, k, p)
|
|
70
|
+
|
|
71
|
+
_lib.scm2cpp_rfe_solve.restype = ctypes.c_int
|
|
72
|
+
_lib.scm2cpp_rfe_solve.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_int), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.c_int, ctypes.c_int]
|
|
73
|
+
def rfe_solve(c, idx, w, l, k, p):
|
|
74
|
+
c = np.ascontiguousarray(c, dtype=np.float64)
|
|
75
|
+
idx = np.ascontiguousarray(idx, dtype=np.int32)
|
|
76
|
+
w = np.ascontiguousarray(w, dtype=np.float64)
|
|
77
|
+
l = np.ascontiguousarray(l, dtype=np.float64)
|
|
78
|
+
return _lib.scm2cpp_rfe_solve(c.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), idx.ctypes.data_as(ctypes.POINTER(ctypes.c_int)), w.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), l.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), k, p)
|
|
79
|
+
|
|
80
|
+
_lib.scm2cpp_rfe.restype = ctypes.c_int
|
|
81
|
+
_lib.scm2cpp_rfe.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_int), ctypes.POINTER(ctypes.c_int), ctypes.c_double, ctypes.c_int, ctypes.c_int, ctypes.c_int, ctypes.c_int]
|
|
82
|
+
def rfe(x, y, coef, support, ranking, alpha, nsel, step, n, p):
|
|
83
|
+
x = np.ascontiguousarray(x, dtype=np.float64)
|
|
84
|
+
y = np.ascontiguousarray(y, dtype=np.float64)
|
|
85
|
+
coef = np.ascontiguousarray(coef, dtype=np.float64)
|
|
86
|
+
support = np.ascontiguousarray(support, dtype=np.int32)
|
|
87
|
+
ranking = np.ascontiguousarray(ranking, dtype=np.int32)
|
|
88
|
+
return _lib.scm2cpp_rfe(x.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), y.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), coef.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), support.ctypes.data_as(ctypes.POINTER(ctypes.c_int)), ranking.ctypes.data_as(ctypes.POINTER(ctypes.c_int)), alpha, nsel, step, n, p)
|
|
89
|
+
|
|
90
|
+
_lib.scm2cpp_eig_hypot.restype = ctypes.c_double
|
|
91
|
+
_lib.scm2cpp_eig_hypot.argtypes = [ctypes.c_double, ctypes.c_double]
|
|
92
|
+
def eig_hypot(a, b):
|
|
93
|
+
return _lib.scm2cpp_eig_hypot(a, b)
|
|
94
|
+
|
|
95
|
+
_lib.scm2cpp_sym_eigen.restype = ctypes.c_int
|
|
96
|
+
_lib.scm2cpp_sym_eigen.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.c_int]
|
|
97
|
+
def sym_eigen(a, v, ev, e, m):
|
|
98
|
+
a = np.ascontiguousarray(a, dtype=np.float64)
|
|
99
|
+
v = np.ascontiguousarray(v, dtype=np.float64)
|
|
100
|
+
ev = np.ascontiguousarray(ev, dtype=np.float64)
|
|
101
|
+
e = np.ascontiguousarray(e, dtype=np.float64)
|
|
102
|
+
return _lib.scm2cpp_sym_eigen(a.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), v.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), ev.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), e.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), m)
|
|
103
|
+
|
|
104
|
+
_lib.scm2cpp_eig_abs.restype = ctypes.c_double
|
|
105
|
+
_lib.scm2cpp_eig_abs.argtypes = [ctypes.c_double]
|
|
106
|
+
def eig_abs(a):
|
|
107
|
+
return _lib.scm2cpp_eig_abs(a)
|
|
108
|
+
|
|
109
|
+
_lib.scm2cpp_eig_order.restype = ctypes.c_int
|
|
110
|
+
_lib.scm2cpp_eig_order.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_int), ctypes.c_int]
|
|
111
|
+
def eig_order(ev, ord, m):
|
|
112
|
+
ev = np.ascontiguousarray(ev, dtype=np.float64)
|
|
113
|
+
ord = np.ascontiguousarray(ord, dtype=np.int32)
|
|
114
|
+
return _lib.scm2cpp_eig_order(ev.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), ord.ctypes.data_as(ctypes.POINTER(ctypes.c_int)), m)
|
|
115
|
+
|
|
116
|
+
_lib.scm2cpp_pca.restype = ctypes.c_int
|
|
117
|
+
_lib.scm2cpp_pca.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.c_int, ctypes.c_int]
|
|
118
|
+
def pca(x, comps, ev, sv, mean, n, p):
|
|
119
|
+
x = np.ascontiguousarray(x, dtype=np.float64)
|
|
120
|
+
comps = np.ascontiguousarray(comps, dtype=np.float64)
|
|
121
|
+
ev = np.ascontiguousarray(ev, dtype=np.float64)
|
|
122
|
+
sv = np.ascontiguousarray(sv, dtype=np.float64)
|
|
123
|
+
mean = np.ascontiguousarray(mean, dtype=np.float64)
|
|
124
|
+
return _lib.scm2cpp_pca(x.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), comps.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), ev.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), sv.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), mean.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), n, p)
|
|
125
|
+
|
|
126
|
+
_lib.scm2cpp_gram_xx.restype = ctypes.c_int
|
|
127
|
+
_lib.scm2cpp_gram_xx.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.c_int, ctypes.c_int]
|
|
128
|
+
def gram_xx(x, g, n, p):
|
|
129
|
+
x = np.ascontiguousarray(x, dtype=np.float64)
|
|
130
|
+
g = np.ascontiguousarray(g, dtype=np.float64)
|
|
131
|
+
return _lib.scm2cpp_gram_xx(x.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), g.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), n, p)
|
|
132
|
+
|
|
133
|
+
_lib.scm2cpp_gram_xy.restype = ctypes.c_int
|
|
134
|
+
_lib.scm2cpp_gram_xy.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.c_int, ctypes.c_int, ctypes.c_int]
|
|
135
|
+
def gram_xy(x, y, c, n, p, q):
|
|
136
|
+
x = np.ascontiguousarray(x, dtype=np.float64)
|
|
137
|
+
y = np.ascontiguousarray(y, dtype=np.float64)
|
|
138
|
+
c = np.ascontiguousarray(c, dtype=np.float64)
|
|
139
|
+
return _lib.scm2cpp_gram_xy(x.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), y.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), c.ctypes.data_as(ctypes.POINTER(ctypes.c_double)), n, p, q)
|
|
140
|
+
|