# TAKT showcase: LightGBM 4.7.0, drop-in with bit-identical output, model analyses up to 18× faster The numbers below are measured. The free package is on PyPI (`pip install lightgbm-takt`); the full version is a commercial licence (see "Availability"). This directory holds the measurement scripts and every reading. **Not affiliated with LightGBM.** TAKT is not affiliated with or endorsed by the LightGBM project or Microsoft. The name LightGBM is used only to identify the software we measured and build on. [LightGBM](https://github.com/lightgbm-org/LightGBM) (MIT) is one of the most widely used gradient-boosting libraries; its Python package (`lightgbm`) wraps the C library `lib_lightgbm.so`. TAKT builds LightGBM 4.7.0 so that analyses that call `predict` many times — permutation importance, partial dependence and ICE curves, MDA feature importance across cross-validation folds, what-if scenario sweeps — and batch prediction run several times faster, with **every prediction identical to the official build, bit for bit**, on the same machine. The Python package and the public API are unchanged (`import lightgbm`); only the library is replaced. No code changes: `sklearn.inspection.permutation_importance`, `partial_dependence`, `PartialDependenceDisplay` and `shap.PermutationExplainer` get the speed-up as they are. ## Headline Factors over the official LightGBM 4.7.0 wheel, by user-mode `cycles:u` with 95% bootstrap CIs, whole process (interpreter start, imports, data loading, the analysis), one core unless noted. The output was identical in every single run. | Workload | Free, Zen 3 | Free, Zen 4 | Full, Zen 3 | Full, Zen 4 | |---|---:|---:|---:|---:| | Permutation importance, quant features (Alpha158), classifier | **3.30×** (3.19–3.33) | **2.74×** (2.70–2.86) | **16.75×** (16.14–16.96) | **18.35×** (17.34–18.71) | | Partial dependence + ICE, the same model, 20 features | **3.67×** (3.58–3.76) | **3.12×** (3.08–3.26) | **16.77×** (16.57–16.93) | **18.31×** (18.06–18.71) | | Permutation importance, OpenML kick (categorical, missing values) | **2.63×** (2.62–2.67) | **2.82×** (2.68–2.87) | **12.97×** (12.85–13.08) | **14.64×** (14.09–15.23) | | What-if scenarios, kick model, 30 scenarios | **2.50×** (2.48–2.52) | **2.60×** (2.53–2.76) | — | — | | MDA importance across 5 cross-validation folds (fitting included) | **2.02×** (2.02–2.04) | **2.05×** (2.01–2.08) | **6.10×** (6.05–6.14) | **5.92×** (5.79–6.01) | | Partial dependence + ICE, California housing regressor | **1.75×** (1.70–1.78) | **1.58×** (1.50–1.64) | **5.43×** (5.37–5.48) | **4.77×** (4.70–4.87) | | `shap.PermutationExplainer`, California housing | 1.02× (1.01–1.03) | 1.03× (1.00–1.05) | **3.23×** (3.16–3.27) | **3.23×** (3.18–3.29) | | `shap.PermutationExplainer`, quant features | — | — | **3.35×** (3.29–3.39) | **4.00×** (3.94–4.09) | | One batch `predict_proba`, quant features, whole process | 1.01× (1.00–1.02) | 1.03× (0.99–1.06) | **2.12×** (2.09–2.14) | **2.45×** (2.40–2.49) | | One batch `predict_proba`, kick, whole process | 1.00× (0.99–1.00) | 1.02× (0.99–1.05) | **1.59×** (1.58–1.59) | **1.73×** (1.72–1.81) | | C API batch prediction, one thread | 1.03× (1.01–1.06) | 1.03× (1.02–1.04) | **4.12×** (4.10–4.22) | **5.38×** (5.25–5.48) | | C API batch prediction, all pinned cores | 1.03× (1.00–1.04) | 1.03× (1.00–1.04) | **4.03×** (3.99–4.06) | **5.32×** (5.13–5.42) | "Free" is measured on models of up to 300 trees (the free package's limit), "full" on the larger models of the same kind (500 and 1,000 trees; the MDA workload fits 300-tree models in both). In the free columns, the rows not in bold are outside the free package's scope and run LightGBM's own code, at the official speed within a few percent. For the multi-threaded C API row, the full version's wall-time factors are lower than the cycle factors (2.29× on Zen 3 with 4 threads, 3.48× on Zen 4 with 2 threads): the threads' total CPU time falls more than the elapsed time. Every wall-time factor is in the tables below. ## Free package vs full version | | Free (`pip install lightgbm-takt`) | Full version (commercial licence) | |---|---|---| | Repeated-call analyses (permutation importance, PDP/ICE, MDA, what-if) | accelerated, models up to 300 trees, one thread | accelerated, any model size, several threads | | Batch prediction (`predict`, `predict_proba`, leaf indices) | LightGBM's own code, normal speed | accelerated: through the C API 4.0–5.4× in CPU time (2.3–4.4× elapsed), leaf indices 2.8–4.1× (1.5–2.4×); a whole Python process 1.6–2.5× | | `shap.PermutationExplainer` | LightGBM's own code, normal speed | accelerated (3.2–4.0×) | | Models with more than 300 trees | LightGBM's own code, normal speed | accelerated | | Everything else in LightGBM (training, SHAP values, every parameter) | LightGBM's own code, full functionality | LightGBM's own code, full functionality | | Output identical to the official wheel | yes, everywhere | yes, everywhere | | Python wheel (Linux x86-64, glibc 2.27+) | yes | yes | | C/C++ library (`lib_lightgbm.so`, same exports) | — | yes | | Other platforms / LightGBM versions | — | on request | | Support, source escrow | — | yes | ## What was measured Python workloads (`tools/wl.py`, `tools/worst.py`) run with the official wheel and with the TAKT wheel; a C driver (`tools/lgbm_block.c`) calls `LGBM_BoosterPredictForMat` with the library swapped through `LD_LIBRARY_PATH`. Every workload prints every result with 17 significant digits (or the SHA-256 of the raw doubles for large arrays), so a byte compare of the output is a bit compare. | Workload | What runs | |---|---| | `pi_alpha`, `pi_alpha300` | `permutation_importance` (neg_log_loss, 3 repeats) on 5,000 rows: a classifier with 1,000 / 300 trees of 63 leaves on 158 Alpha158-style features (qlib formulas) of Binance 5-minute klines (5 pairs), float32 (`tools/features_alpha158.py`) | | `pdp_alpha`, `pdp_alpha300` | `partial_dependence(kind="both", grid_resolution=50)` for 20 features of the same models | | `pi_kick`, `pi_kick300` | `permutation_importance` (roc_auc, 5 repeats) on 8,000 rows of OpenML "kick" (32 features, 18 categorical, 6% missing), pandas input, `LGBMClassifier` 500 / 300 trees | | `whatif_kick300` | 30 what-if scenarios on the kick model (two numeric columns changed in each), `predict_proba` on 8,000 rows each | | `mda_kick` | MDA per cross-validation fold: `KFold(5)` on 40,000 kick rows, each fold fits `LGBMClassifier(300 trees)` and runs `permutation_importance` on its test fold (the fitting is LightGBM's own code in both) | | `pdp_cal`, `pdp_cal300` | `partial_dependence(kind="both", grid_resolution=50)`, California housing `LGBMRegressor` 500 / 300 trees, all 8 features | | `shap_alpha`, `shap_cal`, `shap_cal300` | `shap.PermutationExplainer` with an independent masker (100 / 200 background rows) | | `predict_*` | one `predict_proba` on 50,000 (quant) / 18,246 (kick) rows, whole Python process | | `cblock_*` | C driver: load the model, one `LGBM_BoosterPredictForMat` (normal or leaf indices); `_t1` one thread, `_t4` / `_t2` all pinned cores (4 on Zen 3, 2 on Zen 4) | | `worst_*` | patterns that could cost: 1,500 single-row calls, 300 calls of 16 rows, 40 batches of new shapes, a cycle of 6 different same-shape matrices (1,000 and 300 trees), a 10-tree model on 400,000 rows, a 2,000-feature model with a sweep | All Python workloads run single-threaded (`n_jobs=1`), as in these functions' defaults, unless noted. **Stands.** AMD Threadripper PRO 5975WX (Zen 3), Ubuntu 24.04, glibc 2.39; AMD Ryzen 9 7950X3D (Zen 4), Debian 13, glibc 2.41. Python 3.12, numpy 2.5.4, scipy 1.18.1, scikit-learn 1.9.1, pandas 3.0.6, shap 0.53.0 on both. Each run pinned to one core (the harness too), `takt-harness` 0.2.1, interleaved rounds (5 for the long workloads, 9 after a warm-up for the short ones), 95% bootstrap CIs. The harness compared stdout across the builds in every run. Raw readings: `results/free/zen3`, `results/free/zen4`, `results/full/zen3`, `results/full/zen4` (`.json` bundles and `.log` summaries; paths in them are relative to the measurement directory). ### Free package — AMD Zen 3 | Workload | official wall | TAKT wall | cycles:u factor (95% CI) | wall factor (95% CI) | Output identical | |---|---:|---:|---:|---:|:-:| | pi_alpha300 | 25.01 s | 7.807 s | **3.30×** (3.19–3.33) | 3.20× (3.07–3.29) | yes | | pdp_alpha300 | 43.57 s | 11.86 s | **3.67×** (3.58–3.76) | 3.67× (3.51–3.77) | yes | | pi_kick300 | 38.77 s | 14.86 s | **2.63×** (2.62–2.67) | 2.61× (2.60–2.64) | yes | | whatif_kick300 | 8.415 s | 3.498 s | **2.50×** (2.48–2.52) | 2.41× (2.39–2.45) | yes | | mda_kick | 111.9 s | 55.63 s | **2.02×** (2.02–2.04) | 2.01× (2.01–2.03) | yes | | pdp_cal300 | 25.91 s | 14.97 s | **1.75×** (1.70–1.78) | 1.73× (1.69–1.77) | yes | | predict_alpha300 | 1.449 s | 1.438 s | **1.01×** (1.00–1.02) | 1.01× (0.99–1.02) | yes | | predict_kick300 | 1.759 s | 1.756 s | **1.00×** (0.99–1.00) | 1.00× (0.99–1.01) | yes | | shap_cal300 | 5.280 s | 5.138 s | **1.02×** (1.01–1.03) | 1.03× (1.01–1.03) | yes | | pi_kick | 65.03 s | 63.97 s | **1.01×** (0.99–1.03) | 1.02× (0.98–1.05) | yes | | pi_alpha | 81.91 s | 80.22 s | **1.02×** (1.01–1.03) | 1.02× (1.01–1.03) | yes | | worst_cycle6_300 | 1.856 s | 1.843 s | **1.01×** (1.00–1.02) | 1.01× (1.00–1.02) | yes | | cblock_alpha300_t1 | 504.6 ms | 489.7 ms | **1.03×** (1.01–1.06) | 1.03× (1.00–1.05) | yes | | cblock_alpha300_t4 | 162.8 ms | 161.2 ms | **1.03×** (1.00–1.04) | 1.01× (0.99–1.05) | yes | ### Free package — AMD Zen 4 | Workload | official wall | TAKT wall | cycles:u factor (95% CI) | wall factor (95% CI) | Output identical | |---|---:|---:|---:|---:|:-:| | pi_alpha300 | 18.69 s | 7.283 s | **2.74×** (2.70–2.86) | 2.57× (2.54–2.68) | yes | | pdp_alpha300 | 32.28 s | 10.86 s | **3.12×** (3.08–3.26) | 2.97× (2.95–3.10) | yes | | pi_kick300 | 33.32 s | 12.28 s | **2.82×** (2.68–2.87) | 2.71× (2.59–2.76) | yes | | whatif_kick300 | 7.414 s | 3.265 s | **2.60×** (2.53–2.76) | 2.27× (2.23–2.42) | yes | | mda_kick | 92.95 s | 45.79 s | **2.05×** (2.01–2.08) | 2.03× (1.99–2.07) | yes | | pdp_cal300 | 17.35 s | 11.19 s | **1.58×** (1.50–1.64) | 1.55× (1.47–1.60) | yes | | predict_alpha300 | 1.585 s | 1.537 s | **1.03×** (0.99–1.06) | 1.03× (0.98–1.04) | yes | | predict_kick300 | 1.887 s | 1.845 s | **1.02×** (0.99–1.05) | 1.02× (0.98–1.05) | yes | | shap_cal300 | 3.840 s | 3.726 s | **1.03×** (1.00–1.05) | 1.03× (1.02–1.05) | yes | | pi_kick | 59.47 s | 58.18 s | **1.02×** (0.97–1.05) | 1.02× (0.94–1.09) | yes | | pi_alpha | 71.12 s | 68.50 s | **1.04×** (1.01–1.06) | 1.04× (1.01–1.08) | yes | | worst_cycle6_300 | 1.774 s | 1.750 s | **1.01×** (1.00–1.09) | 1.01× (0.98–1.04) | yes | | cblock_alpha300_t1 | 381.3 ms | 373.9 ms | **1.03×** (1.02–1.04) | 1.02× (0.99–1.03) | yes | | cblock_alpha300_t2 | 212.9 ms | 205.6 ms | **1.03×** (1.00–1.04) | 1.03× (0.98–1.09) | yes | ### Full version — AMD Zen 3 | Workload | official wall | TAKT wall | cycles:u factor (95% CI) | wall factor (95% CI) | Output identical | |---|---:|---:|---:|---:|:-:| | pi_alpha | 82.44 s | 5.274 s | **16.75×** (16.14–16.96) | 15.63× (15.02–16.22) | yes | | pdp_alpha | 146.9 s | 8.972 s | **16.77×** (16.57–16.93) | 16.38× (16.14–16.55) | yes | | pi_kick | 63.41 s | 5.098 s | **12.97×** (12.85–13.08) | 12.44× (12.35–12.54) | yes | | mda_kick | 113.1 s | 18.75 s | **6.10×** (6.05–6.14) | 6.03× (5.86–6.08) | yes | | pdp_cal | 45.75 s | 8.592 s | **5.43×** (5.37–5.48) | 5.33× (5.26–5.38) | yes | | shap_alpha | 8.800 s | 2.919 s | **3.35×** (3.29–3.39) | 3.02× (2.98–3.06) | yes | | shap_cal | 8.375 s | 2.755 s | **3.23×** (3.16–3.27) | 3.04× (2.99–3.09) | yes | | predict_alpha | 2.679 s | 1.405 s | **2.12×** (2.09–2.14) | 1.91× (1.88–1.93) | yes | | predict_kick | 2.116 s | 1.417 s | **1.59×** (1.58–1.59) | 1.49× (1.48–1.50) | yes | | cblock_alpha_normal_t1 | 1.694 s | 472.1 ms | **4.12×** (4.10–4.22) | 3.59× (3.52–3.63) | yes | | cblock_alpha_leaf_t1 | 1.696 s | 759.0 ms | **3.02×** (2.97–3.04) | 2.23× (2.20–2.26) | yes | | cblock_kick_normal_t1 | 857.7 ms | 216.4 ms | **4.36×** (4.26–4.37) | 3.96× (3.88–4.03) | yes | | cblock_alpha_normal_t4 | 477.3 ms | 208.6 ms | **4.03×** (3.99–4.06) | 2.29× (2.23–2.33) | yes | | cblock_alpha_leaf_t4 | 549.2 ms | 367.2 ms | **2.76×** (2.75–2.80) | 1.50× (1.49–1.53) | yes | | cblock_kick_normal_t4 | 244.9 ms | 98.05 ms | **4.05×** (4.03–4.08) | 2.50× (2.38–2.52) | yes | | worst_rows1 | 1.034 s | 1.041 s | **1.00×** (0.99–1.01) | 0.99× (0.99–1.01) | yes | | worst_rows16 | 1.101 s | 1.042 s | **1.07×** (1.07–1.08) | 1.06× (1.04–1.06) | yes | | worst_newshapes | 4.217 s | 1.394 s | **3.40×** (3.31–3.42) | 3.03× (2.98–3.07) | yes | | worst_cycle6 | 4.214 s | 1.419 s | **3.32×** (3.30–3.35) | 2.97× (2.94–3.00) | yes | | worst_tiny10 | 1.121 s | 1.096 s | **1.05×** (1.05–1.07) | 1.02× (1.01–1.03) | yes | | worst_wide2000 | 2.153 s | 1.471 s | **1.61×** (1.60–1.62) | 1.46× (1.45–1.48) | yes | ### Full version — AMD Zen 4 | Workload | official wall | TAKT wall | cycles:u factor (95% CI) | wall factor (95% CI) | Output identical | |---|---:|---:|---:|---:|:-:| | pi_alpha | 71.21 s | 4.521 s | **18.35×** (17.34–18.71) | 15.75× (15.21–16.19) | yes | | pdp_alpha | 127.5 s | 7.625 s | **18.31×** (18.06–18.71) | 16.73× (16.54–17.09) | yes | | pi_kick | 58.31 s | 4.596 s | **14.64×** (14.09–15.23) | 12.69× (12.27–13.11) | yes | | mda_kick | 92.06 s | 16.28 s | **5.92×** (5.79–6.01) | 5.66× (5.53–5.73) | yes | | pdp_cal | 32.67 s | 7.412 s | **4.77×** (4.70–4.87) | 4.41× (4.34–4.52) | yes | | shap_alpha | 7.297 s | 2.415 s | **4.00×** (3.94–4.09) | 3.02× (3.00–3.10) | yes | | shap_cal | 6.235 s | 2.345 s | **3.23×** (3.18–3.29) | 2.66× (2.57–2.71) | yes | | predict_alpha | 2.638 s | 1.460 s | **2.45×** (2.40–2.49) | 1.81× (1.77–1.84) | yes | | predict_kick | 2.181 s | 1.500 s | **1.73×** (1.72–1.81) | 1.45× (1.42–1.48) | yes | | cblock_alpha_normal_t1 | 1.488 s | 342.4 ms | **5.38×** (5.25–5.48) | 4.35× (4.17–4.41) | yes | | cblock_alpha_leaf_t1 | 1.589 s | 652.1 ms | **4.09×** (4.02–4.22) | 2.44× (2.40–2.48) | yes | | cblock_kick_normal_t1 | 801.6 ms | 181.5 ms | **4.87×** (4.67–4.90) | 4.42× (4.27–4.47) | yes | | cblock_alpha_normal_t2 | 787.4 ms | 226.0 ms | **5.32×** (5.13–5.42) | 3.48× (3.31–3.60) | yes | | cblock_alpha_leaf_t2 | 920.3 ms | 477.5 ms | **3.92×** (3.75–4.03) | 1.93× (1.85–2.00) | yes | | cblock_kick_normal_t2 | 424.5 ms | 113.4 ms | **4.75×** (4.67–4.80) | 3.74× (3.62–3.81) | yes | | worst_rows1 | 1.153 s | 1.153 s | **1.00×** (0.98–1.03) | 1.00× (0.97–1.03) | yes | | worst_rows16 | 1.207 s | 1.158 s | **1.07×** (1.05–1.09) | 1.04× (1.00–1.09) | yes | | worst_newshapes | 4.048 s | 1.469 s | **3.66×** (3.64–3.71) | 2.75× (2.69–2.78) | yes | | worst_cycle6 | 4.031 s | 1.429 s | **3.98×** (3.92–4.03) | 2.82× (2.71–2.87) | yes | | worst_tiny10 | 1.230 s | 1.179 s | **1.06×** (1.05–1.09) | 1.04× (1.00–1.09) | yes | | worst_wide2000 | 2.159 s | 1.516 s | **1.75×** (1.72–1.79) | 1.42× (1.39–1.49) | yes | ## Equivalence "Same" means byte-identical output, every number at 17 significant digits. - **Equivalence matrix** (`tools/eqmatrix.py`): 4,497 prediction cases, 1.06 billion values, on 23 models trained on public data — LightGBM's own examples (regression, binary, multiclass, lambdarank), scikit-learn's bundled sets (DART, random forest, linear trees), California housing (1,024 leaves; poisson, tweedie, gamma, huber, quantile, cross-entropy objectives; 30% NaN with and without `use_missing`; 30% zeros with `zero_as_missing`), OpenML adult, credit-g and kick (categorical- and missing-heavy). Inputs: the test split plus adversarial rows (NaN, ±inf, −0.0, subnormals, values at ±1e-35 and their float neighbours, values exactly on and next to split thresholds, out-of-range and non-integer categories). Every input type (numpy float64/float32 in C and Fortran order, CSR, CSC, pandas, pyarrow), prediction type (normal, raw, leaf, contributions), iteration range, 1 and 4 threads, prediction early stopping, repeated calls in the pattern of permutation importance and partial dependence, and models changed between calls (`set_leaf_output`, `rollback_one_iter`, `update`, `refit`). Identical for the free and the full library on both machines. - **LightGBM's own test suites:** the C++ test suite (34 of 34) passes with both TAKT builds as with the unmodified source; the Python test suite gives 1,689 passed, 19 skipped with the official wheel and with both TAKT wheels (the same 4 graphviz plotting tests fail with all of them on a machine without the `dot` binary). - **Concurrency:** 8–16 Python threads predicting on shared models, compared with the official sequential results: identical. Soak runs with `TAKT_LGBM_VERIFY=1`, which recomputes every accelerated call with LightGBM's original code: full version four runs, 10.5 hours in total, 2.4 million calls; free package 30 minutes, 125,000 calls; no difference. - **ABI:** the library exports exactly the same 6,469 symbols as the official one, needs the same libraries and symbol versions (glibc 2.27 at most), and is built with the official compiler (gcc 12.2.1) in the manylinux_2_28 image with the official configuration. **Bit-identity is per system.** The TAKT build reproduces the official build's output on the same system, bit for bit. Results that pass through the system maths library (for example probabilities) depend on it, so compare on the same machine. ## Where the speed-up applies, and where it does not - **Full version:** batch prediction through every matrix entry point (numpy and pandas, row pointers, CSR, CSC, Arrow), normal, raw and leaf-index outputs, all boosting types and objectives, numerical and categorical splits with every missing-value mode, linear trees, any number of trees and leaves, iteration ranges, any thread count; and the repeated-call analyses on top of that. - **Free package:** the repeated-call analyses on dense inputs (numpy, pandas) with models of up to 300 trees; everything else is LightGBM's own code at its normal speed. - **LightGBM's own code, same result, same speed (both):** SHAP contributions (`pred_contrib`), prediction early stopping, very small calls (under 8 rows), the single-row fast API, prediction from files, models with more than 100,000 features. - **Worst cases** (`worst_*` above): full version 1.00–3.98×, free package 1.01×; none is slower than the official library beyond measurement noise. - **Optional environment variables:** `TAKT_LGBM_VERIFY=1` recomputes every accelerated call with LightGBM's original code and reports any difference (slow; for checking); `TAKT_LGBM_DISABLE=1` turns the acceleration off; `TAKT_LGBM_CACHE_MB=N` limits the extra memory the acceleration may use (default and, in the free package, maximum 1 GB; 0 turns it off). **LightGBM's own concurrency limits.** In LightGBM 4.7.0, with the official library: concurrent predictions on one booster with different `start_iteration`/`num_iteration` (LightGBM issue #6142), concurrent calls with different `num_threads`, and changing a booster (training, `set_leaf_output`, `refit`) while another thread predicts with it can crash or return wrong values. Code that avoids these patterns runs the same with TAKT. The parts of TAKT that run LightGBM's own code keep this behaviour; the full version's accelerated calls take the iteration range from each call (a 16-thread test of the first pattern that crashes the official library gave 0 differences with them). ## Availability - **Free:** `pip install lightgbm-takt` (after `pip uninstall -y lightgbm`). Repeated-call analyses accelerated on models up to 300 trees; everything else runs LightGBM's own code at its normal speed, with full LightGBM functionality available. Linux x86-64, Python 3.10–3.14. The library in the free package carries the TAKT Free Binary Licence for TAKT's contributions; LightGBM's code stays under its MIT licence. - **Full version:** a commercial licence: every model size and the analyses on several threads, faster batch prediction and explainers, the C/C++ library (`lib_lightgbm.so`, same exports), builds for other platforms and LightGBM versions, support, and source escrow (the modified source in an encrypted escrow box, released to you on the conditions of our Terms of Service). - **Prices:** - **Team, $399 a month billed yearly ($4,788):** the full version on one platform, with every new LightGBM release rebuilt and checked bit for bit again. - **Enterprise, from $1,500 a month billed yearly:** other platforms and LightGBM versions, an SLA, source escrow and acceptance on your own hardware. - A licence, a quote, or a free speed check of your own code: - New measurements of other libraries, one a week: ## Reproducing the baseline ```sh # The verify script: a 300-tree model on synthetic data, permutation importance and a PDP, compared bytewise. python -m venv a && a/bin/pip install -q lightgbm==4.7.0 scikit-learn && a/bin/python tools/verify.py > a.txt python -m venv c && c/bin/pip install -q lightgbm-takt scikit-learn && c/bin/python tools/verify.py > c.txt diff a.txt c.txt && echo identical # The workloads: prepare the models once (official wheel), then run any workload with each wheel. python tools/wl.py prep . # the kick and California models (500 trees) python tools/wl.py prep_free . # the 300-tree models (the quant model needs the quant data, see below) python tools/wl.py pi_kick300 . > out.txt ``` The kick and California housing workloads download their data themselves (OpenML, scikit-learn). The quant-feature workloads (`*_alpha*`) read features computed with `tools/features_alpha158.py` from Binance 5-minute klines of five pairs, and the trained model files; these data files are not in this directory (on request). `tools/table.py` and `tools/pubtable.py` print the tables above from the readings in `results/`. ## Contents - `tools/`: the workload scripts (`wl.py`, `worst.py`, `features_alpha158.py`), the C driver (`lgbm_block.c`), the equivalence and concurrency checks (`eqmatrix.py`, `concurrency.py`), the verify script (`verify.py`), and the table scripts (`table.py`, `pubtable.py`). - `results/free/`, `results/full/`: `takt-harness` readings (`.json`) and summaries (`.log`) for every workload on both machines; `results/equiv/SUMMARY.md`: the equivalence summary. - `LICENSE`: MIT, for the scripts and readings in this directory.