The demo scenarios
Every demo ships as a ready-to-run config file in the distribution's
demos/ directory — run any of them from the package root:
./fst4 --config demos/demo10.cfg
The numbering continues the FST3 demo catalog: configs marked
FST3 parity reproduce the corresponding published FST3 example's
protocol through the fst4 CLI, and the FST4-native additions
fill the freed numbers within each topical group. Demo names ending in
t use threads. Every flag used below is documented on the
FST4 CLI page. Three scenarios additionally ship as
compiled C++ exemplars of the library API (demo10.cpp,
demo52t.cpp, demo55.cpp) producing the same
results as their configs; their sources are shown in the
Examples section of the API reference
with every class linked to its documentation, and linked from the entries
below.
Data note. The FST3-era speech data set left the distribution
with 4.2 (the affected demos now run on the WDBC data with protocols
otherwise unchanged), and the sonar data's historical class split was
corrected to the official UCI one — so numbers published in FST3-era
materials for the speech and sonar demos are not reproducible from the
shipped data. Correctness over parity; see the package's
data/NOTICE for provenance of every bundled data set.
Basic sub-optimal feature selection (demo1x)
The entry-level scenarios: filter- and wrapper-based selection with sequential and floating searches, the metric palette, and the new deterministic wrapper models on moderate-dimensional data.
demo10 — Example 10: Basic Filter-based feature selectionFST3 parity · C++ exemplar ships
Generalized Mahalanobis filter + SFS at target d=7 on 50/50-split WDBC data, validated by 3-NN on the held-out part (subset 3 10 16 20 21 26 27, value 12.1045, holdout accuracy 0.8947). FST3 demo parity config; the compiled exemplar demo10.cpp still ships and produces the same result.
./fst4 --config demos/demo10.cfg
demos/demo10.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
criterion = "gmahalanobis"
search = "sfs"
target-d = 7
validate = "knn"
demo10.cpp — the compiled C++ exemplar in the API reference →
demo11 — Example 11: Wrapper-based feature selection with Floating SearchFST3 parity
SVM wrapper (LINEAR kernel, C preset to 2.85117 as in the demo) + SFFS in d-optimizing mode on sonar data; criterion estimated by 3-fold CV on the train half of a single random 50/50 split, final SVM validation on the holdout. NOTE: LINEAR kernel may freeze LibSVM training on some data (see Known Issues). FST3 demo parity config.
./fst4 --config demos/demo11.cfg
demos/demo11.cfg:
data = "data/sonar_60.arff"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 50
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-svm"
svm-kernel = "linear"
svm-c = 2.85117
search = "sffs"
validate = "same"
demo11reg — Example 11: Wrapper-based (regression) feature selection with Floating SearchFST3 parity
Weighted-neighbours regression wrapper (the class label = dependent variable) + SFFS in d-optimizing mode; kernel-multiplier sweep {0.3, 0.35, 0.4} runs one full search per value and the best-by-train-value wins (demo11reg protocol), validated by regressor train/test on the 50/50 holdout. FST3 demo parity config.
./fst4 --config demos/demo11reg.cfg
demos/demo11reg.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-regressor"
search = "sffs"
regr-multipliers = "0.3,0.35,0.4"
validate = "same"
demo11t — Example 11t: Threaded wrapper-based feature selection with Floating SearchFST3 parity · threaded · long-running
3-NN wrapper + SFFS in d-optimizing mode with 2 evaluation threads on the 10k-feature reuters text data; criterion estimated by leave-one-out on the train half of a single random 50/50 split, final kNN validation on the holdout. NOTE: compute-bound — leave-one-out kNN over 10105 features makes this run for many hours; it demonstrates the threaded evaluator, not a quick result. FST3 demo parity config.
./fst4 --config demos/demo11t.cfg
demos/demo11t.cfg:
data = "data/reuters_apte.arff"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 50
splitter2 = "leave1out"
criterion = "wrapper-knn"
knn-k = 3
search = "sffs"
validate = "same"
threads = 2
demo12t — Example 12t: Threaded SVM-wrapper-based feature selection with Dynamic Oscillating SearchFST3 parity · threaded
SVM wrapper (RBF kernel) with pre-search C/gamma grid optimization + sequential search with 2 evaluation threads on waveform data (50/50 split, 3-fold CV criterion estimation), final SVM validation on the holdout. NOTE: the demo's active code path is SFS despite the DOS in its title. FST3 demo parity config.
./fst4 --config demos/demo12t.cfg
demos/demo12t.cfg:
data = "data/waveform_40.arff"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-svm"
svm-kernel = "rbf"
svm-optimize = "pre"
search = "sfs"
validate = "same"
threads = 2
demo13t — FST4 4.1 demo: Threaded wrapper-based feature selection with a logistic regression classifierFST4-native · threaded
(A new FST4 demo number — no demo13 existed in FST3; suffix 't' = threaded, as in demo11t/demo12t.) Multinomial logistic regression wrapper (new in 4.1: dependency-free damped-Newton training, internally standardized per split, RNG-free) + SFFS in d-optimizing mode with 2 evaluation threads on the WDBC breast-cancer diagnostic data — a two-class problem with continuous clinical features that is close to linearly separable, i.e. exactly the regime where logistic regression is the textbook classifier choice (50/50 split, 3-fold CV criterion estimation); final logistic-regression validation on the holdout. Training is deterministic by construction, so results are byte-identical at any --seed and --threads. (For a true multiclass logistic regression case, swap in data/waveform_40.trn — its 3 classes derive from linear combinations of base waves and also suit a linear model well.)
./fst4 --config demos/demo13t.cfg
demos/demo13t.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-logreg"
search = "sffs"
validate = "same"
threads = 2
demo14 — FST4 4.2 demo: Balanced-Accuracy vs. Plain-Accuracy Wrapper Selection ComparedFST4-native
(A new FST4 demo number — no demo14 existed in the public FST3.) Does the wrapper metric change WHICH features get selected? Scenario A (this file): 3-NN wrapper optimizing BALANCED accuracy (macro-averaged recall, the imbalance-robust choice — WDBC is a 357/212 benign/malignant split, so plain accuracy over-rewards the majority class). Scenario B (tests/fst4_compare_demo14_plain.cfg): identical except plain accuracy. Both repeat selection over the SAME 10 random 80/20 splits (3-fold CV criterion estimation) and are compared by cross-scenario tracker similarity (IATI/ICW/IANHI, the demo55 protocol): similarity < 1 quantifies how much the metric choice alone redirects the search. See the --wrapper-metric entry in doc/FST4_CLI.md for the metric palette; flip the wrapper-metric key to f1 for the positive-class (malignant) F1 variant.
./fst4 --config demos/demo14.cfg
demos/demo14.cfg:
data = "data/wdbc_30.trn"
splitter = "randrand"
rr-splits = 10
rr-train = 80
rr-test = 20
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
wrapper-metric = "balanced-accuracy"
search = "sfs"
target-d = 5
repeat-over-splits = true
tracker = "stabileval"
compare-config = "tests/fst4_compare_demo14_plain.cfg"
demo15 — FST4 4.2 demo: Wrapper Selection Optimizing AUC (Area Under the ROC Curve)FST4-native
(A new FST4 demo number — no demo15 existed in FST3.) Threshold-free wrapper selection: the logistic-regression wrapper scores each candidate subset by the exact two-class AUC (Mann-Whitney rank statistic with midrank ties, computed from the model's per-sample decision scores) instead of accuracy at the default threshold. Same WDBC data as demo13t/demo14 but a different classifier under the wrapper (logistic regression exposes smooth probability scores — the natural AUC pairing; positive class = class index 1 = malignant). SFFS in d-optimizing mode, 50/50 split, 3-fold CV criterion estimation; the final validation line reports holdout accuracy AND AUC of the selected subset. Deterministic: logreg training is RNG-free and AUC tie handling is exact, so results are byte-identical at any --seed. See the --wrapper-metric entry in doc/FST4_CLI.md for the metric palette. AUC covers any class count: two-class is the exact binary AUC, K>2 the one-vs-rest macro AUC (demo27 demonstrates the multiclass case). This demo reads data/wdbc_30.csv — the CSV conversion of wdbc_30.trn (identical values and sample order) — demonstrating the CSV loader on real data; the results are identical to the TRN version.
./fst4 --config demos/demo15.cfg
demos/demo15.cfg:
data = "data/wdbc_30.csv"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-logreg"
wrapper-metric = "auc"
search = "sffs"
validate = "same"
demo16 — FST4 4.2 demo: Cost-Sensitive Wrapper Selection with Per-Class WeightsFST4-native
(A new FST4 demo number — no demo16 existed in FST3.) When error costs are asymmetric, encode them into the selection pressure: class-weights 1,5 makes every misclassified MALIGNANT case (class index 1, the 212-sample minority of WDBC) five times as costly as a misclassified benign one, so the normal-Bayes wrapper prefers subsets that protect recall on the malignant class. This differs from demo14's balanced accuracy: weights encode DOMAIN costs you choose (a screening scenario would use a much larger ratio); balanced accuracy merely equalizes class importance. The validation line reports plain holdout accuracy AND the weighted accuracy of the selected subset. 50/50 split, 3-fold CV criterion estimation, SFFS in d-optimizing mode. See the --wrapper-metric entry in doc/FST4_CLI.md for the palette. (class-weights deliberately does not combine with balanced-accuracy or auc — see --help.)
./fst4 --config demos/demo16.cfg
demos/demo16.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-bayes"
class-weights = "1,5"
search = "sffs"
validate = "same"
demo17 — FST4 4.2 demo: Regression Feature Selection Scored by R-squaredFST4-native
(A new FST4 demo number — no demo17 existed in FST3.) The regression counterpart of the 4.2 wrapper-metric family: the weighted-neighbours regression wrapper (demo11reg's engine) scores candidate subsets by the coefficient of determination R^2 — an interpretable, scale-free criterion (1 = perfect prediction, 0 = no better than predicting the mean) — instead of the plain negated-error value. neg-rmse and neg-mae are the alternative regression metrics; all are higher-is-better as the search maximizes. WDBC data, 50/50 split, 3-fold CV criterion estimation, SFS to 5 features; the validation line reports the plain regressor value AND the holdout R^2 of the selected subset. See the --wrapper-metric entry in doc/FST4_CLI.md for the metric palette.
./fst4 --config demos/demo17.cfg
demos/demo17.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-regressor"
wrapper-metric = "r2"
search = "sfs"
target-d = 5
validate = "same"
demo18 — FST4 4.2 demo: Random Forest Wrapper Feature SelectionFST4-native
(A new FST4 demo number — no demo18 existed in FST3.) The 4.2 dependency-free Random Forest as a wrapper criterion: 100 CART trees (Gini impurity, bagging, sqrt-mtry feature subsampling per node) score each candidate subset by 3-fold cross-validated accuracy on the spambase corpus (4601 e-mails, 57 word/char-frequency features, spam vs. ham) — the classic "practitioner" setting where a nonlinear ensemble is the model of choice. Determinism by design: RF training seeds derive from (subset content, --seed, split index), never from FST4's global fst_rand stream, so every subset evaluation is a pure function of its inputs — results are bit-identical at any --threads value and independent of evaluation order (--threads 4 below only changes the wall time). SFS to 10 features; final RF validation on the 50/50 holdout. Tune with --rf-trees/-mtry/-max-depth/-min-leaf; all 4.2 wrapper metrics apply (e.g. wrapper-metric = "f1" for the spam class). Runs in well under a minute on a desktop (threads 4).
./fst4 --config demos/demo18.cfg
demos/demo18.cfg:
data = "data/spambase_57.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-rf"
rf-trees = 100
search = "sfs"
target-d = 10
validate = "same"
threads = 4
demo19 — FST4 4.2 demo: Ridge Regression Wrapper Scored by R-squaredFST4-native
(A new FST4 demo number — no demo19 existed in FST3.) The linear counterpart of demo17: closed-form ridge regression (L2-regularized least squares solved by Cholesky on internally standardized features, bias unpenalized; ridge-lambda tunes the penalty) as the wrapper criterion, scored by R^2 — wrapper-ridge defaults to that metric, no wrapper-metric key needed. Same WDBC data, split and search as demo17, so the two configs compare the linear model against the weighted-neighbours regressor directly (on this data ridge reaches a higher holdout R^2 with the same subset size). Deterministic and RNG-free like the logistic-regression classifier: results are byte-identical at any --seed and --threads. The validation line reports the plain regressor value AND the holdout R^2. See the --wrapper-metric entry in doc/FST4_CLI.md for the metric palette.
./fst4 --config demos/demo19.cfg
demos/demo19.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-ridge"
search = "sfs"
target-d = 5
validate = "same"
More sub-optimal methods (demo2x)
Advanced sequential scenarios: oscillating and dynamic oscillating search, retreating search, randomized restarts, hybrid and ensemble evaluation, SVM parameter optimization.
demo20 — Example 20: Retreating Sequential SearchFST3 parity
3-NN wrapper + SFRS (Sequential Forward Retreating Search) in d-optimizing mode on WDBC data; criterion estimated by leave-one-out on the train half of a 50/50 split, final kNN validation on the holdout. FST3 demo parity config.
./fst4 --config demos/demo20.cfg
demos/demo20.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "leave1out"
criterion = "wrapper-knn"
knn-k = 3
search = "sfrs"
validate = "same"
demo21 — Example 21: Generalized sequential feature subset searchFST3 parity
5-NN wrapper + generalized SFFS (g-tuples of 2 features added/removed per step) in d-optimizing mode on WDBC data (50/50 split, 3-fold CV criterion estimation), final 5-NN validation on the holdout. FST3 demo parity config.
./fst4 --config demos/demo21.cfg
demos/demo21.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 5
search = "sffs"
generalization-level = 2
validate = "same"
demo22 — Example 22: Randomized feature selection with Oscillating SearchFST3 parity
Bhattacharyya filter + Oscillating Search (delta=10) at target d=30 on sonar data (single random 75/25 split, no inner splitter), rerun from random initial subsets until 4 consecutive runs fail to improve (reproduces the demo's 5-consecutive-runs stop rule under the CLI's counting), final 3-NN validation on the holdout. FST3 demo parity config.
./fst4 --config demos/demo22.cfg
demos/demo22.cfg:
data = "data/sonar_60.trn"
splitter = "randrand"
rr-splits = 1
rr-train = 75
rr-test = 25
criterion = "bhattacharyya"
search = "os"
os-delta = 10
target-d = 30
restarts-nonimproving = 4
validate = "knn"
demo23 — Example 23: Combined feature subset contents, size and SVM parameters optimizationFST3 parity
SVM wrapper (RBF kernel) + Dynamic Oscillating Search (delta=3, d-optimizing) on sonar data (single random 50/40 split, 3-fold CV criterion estimation); alternating protocol: SVM C/gamma grid optimization and search repeat while the train criterion improves, best parameters restored before the final SVM validation on the holdout. FST3 demo parity config.
./fst4 --config demos/demo23.cfg
demos/demo23.cfg:
data = "data/sonar_60.trn"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-svm"
svm-kernel = "rbf"
svm-optimize = "alternating"
search = "dos"
dos-delta = 3
validate = "same"
demo24 — Example 24: Monte Carlo - random feature subset searchFST3 parity
3-NN wrapper + Monte Carlo search over random subsets of cardinality 4..10 with a 100-second wall-clock budget (no trial limit) on WDBC data (50/50 split, 3-fold CV criterion estimation), final kNN validation on the holdout. NOTE: the wall-clock stopping condition makes results load-dependent — this config documents the protocol; it is not byte-reproducible across runs. FST3 demo parity config.
./fst4 --config demos/demo24.cfg
demos/demo24.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
search = "montecarlo"
mc-trials = 0
mc-seconds = 100
mc-card-min = 4
mc-card-max = 10
validate = "same"
demo24t — Example 24t: Threaded Monte Carlo - random feature subset searchFST3 parity · threaded
3-NN wrapper + Monte Carlo search with 4 evaluation threads; random subsets are drawn by per-feature inclusion probability 0.5 (instead of a cardinality range) under a 100-second wall-clock budget on WDBC data (50/50 split, 3-fold CV criterion estimation), final kNN validation on the holdout. NOTE: the wall-clock stopping condition makes results load-dependent. FST3 demo parity config.
./fst4 --config demos/demo24t.cfg
demos/demo24t.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
search = "montecarlo"
mc-trials = 0
mc-seconds = 100
mc-card-prob = 0.5
validate = "same"
threads = 4
demo25t — Example 25t: Fast pre-selection followed by Dynamic Oscillating SearchFST3 parity · threaded · long-running
SVM wrapper (SIGMOID kernel) on optdigits (50/50 split, 3-fold CV criterion estimation): BIF individual ranking pre-selects the top 20 features to seed a threaded (4 threads) Dynamic Oscillating Search (delta=3, d-optimizing); SVM parameters are grid-optimized on the full set and re-optimized on the BIF seed (--svm-optimize pre), final SVM validation on the holdout. NOTE: long-running (tens of minutes; the golden scenario runs in the slow tier). FST3 demo parity config.
./fst4 --config demos/demo25t.cfg
demos/demo25t.cfg:
data = "data/optdigits_64.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-svm"
svm-kernel = "sigmoid"
svm-optimize = "pre"
search2 = "bif"
search2-d = 20
search = "dos"
dos-delta = 3
validate = "same"
threads = 4
demo26 — Example 26: Wrapper-based (normal Bayes) feature selection with Floating Search, verified by 2 classifiersFST3 parity
Normal Bayes wrapper + SFFS in d-optimizing mode on WDBC data (50/50 split, 3-fold CV criterion estimation); the result is validated on the holdout by BOTH the Bayes classifier and 3-NN (dual validation). FST3 demo parity config.
./fst4 --config demos/demo26.cfg
demos/demo26.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-bayes"
search = "sffs"
validate = "same,knn"
demo27 — FST4 4.2 demo: Multiclass Selection by One-vs-Rest Macro AUC (no FST3 counterpart)FST4-native
(A new FST4 demo number — this is NOT an FST3 parity config; the number was never used by a publicly released FST3 demo.) On data with more than two classes, wrapper-metric = "auc" selects features by the one-vs-rest MACRO AUC — the unweighted mean over classes of the exact binary AUC (midrank tie rule) computed from each class's own score column against the rest; classes absent from a test part are skipped (the balanced-accuracy convention). Scores come from the classifier's classify_scores seam — here the logistic regression's per-class linear scores; all deterministic, RNG-free. On two-class data the same flag is the plain binary AUC (demo15). Contrast with demo15 (binary AUC on WDBC): same flag, richer data.
./fst4 --config demos/demo27.cfg
demos/demo27.cfg:
data = "data/waveform_40.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-logreg"
wrapper-metric = "auc"
search = "sfs"
target-d = 5
validate = "same"
demo28 — FST4 4.2 demo: RBF Kernel SVM Wrapper Feature Selection (no LibSVM needed)FST4-native
(A new FST4 demo number — this is NOT an FST3 parity config; the number was never used by a publicly released FST3 demo.) The 4.2 dependency-free RBF kernel SVM as a wrapper criterion: C-SVC trained by kernel dual coordinate descent with the penalized-bias kernel offset (implemented from scratch — no LibSVM code anywhere). The coordinate order is fixed cyclic — no RNG, so results are byte-identical at any --seed and --threads. Together with wrapper-linsvm (demo38) this covers both SVM kernels of practical value natively; LibSVM remains an optional extension for cross-checks and the FST3 parity configs only. Same sonar protocol as the LibSVM-based demo23 (minus its --svm-optimize grid search), so the native kernel machine contrasts directly with the LibSVM path: results are NOT bit-comparable by design (different solver, penalized bias, internal standardization) — expect near-identical accuracy. Gamma defaults to 1/subset-size on the internally standardized features; tune with rbfsvm-c / rbfsvm-gamma / rbfsvm-loss (l1|l2) / rbfsvm-maxiter / rbfsvm-tol; all 4.2 wrapper metrics apply (e.g. wrapper-metric = "auc").
./fst4 --config demos/demo28.cfg
demos/demo28.cfg:
data = "data/sonar_60.trn"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-rbfsvm"
search = "dos"
dos-delta = 3
validate = "same"
demo29 — FST4 4.2 demo: RBF SVM Wrapper with Alternating C/gamma Optimization (no LibSVM needed)FST4-native
(A new FST4 demo number — this is NOT an FST3 parity config; the number was never used by a publicly released FST3 demo.) The full demo23 protocol on the native RBF kernel SVM: rbfsvm-optimize = "alternating" tunes C and gamma by the same space-filling random search as LibSVM's --svm-optimize (candidates repel already-tested points, weighted against bad regions; all randomness from fst_rand on the master thread, so runs are deterministic at matched --seed), first on the full feature set, then re-optimizing and re-searching while the training criterion improves. Completes the demo28 story: demo28 = the protocol with fixed defaults, demo29 = with the hyperparameter grid — no LibSVM involved in either. Results are deliberately NOT bit-comparable to demo23's LibSVM numbers. Note the classic small-sample lesson (the demo5x anti-overfitting theme): the optimized criterion rises while the independent holdout may drop — hyperparameter tuning on ~100 training samples overfits easily.
./fst4 --config demos/demo29.cfg
demos/demo29.cfg:
data = "data/sonar_60.trn"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-rbfsvm"
rbfsvm-optimize = "alternating"
search = "dos"
dos-delta = 3
validate = "same"
High-dimensional tasks and DAF ranking (demo3x)
Very-high-dimensional feature selection: Dependency-Aware Feature ranking over Monte Carlo probes, multinomial text-data criteria, and the budgeted stochastic (sampled) sequential search line.
demo30 — Example 30: Feature selection on binary and/or natural-valued dataFST3 parity
Multinomial naive Bayes wrapper + Dynamic Oscillating Search (delta=10, d-optimizing) on binary mushroom data (single random 50/40 split, 5-fold CV criterion estimation), final multinomial NB validation on the holdout. FST3 demo parity config.
./fst4 --config demos/demo30.cfg
demos/demo30.cfg:
data = "data/mushroom_125.trn"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
splitter2 = "cv"
splitter2-cv-folds = 5
criterion = "wrapper-multinom"
search = "dos"
dos-delta = 10
validate = "same"
demo31 — Example 31: Individual ranking (BIF) in very high-dimensional feature selectionFST3 parity
Multinomial Bhattacharyya filter + BIF individual ranking of the top 500 features on the 10k-feature reuters text data (single random 50/40 split, no inner splitter), validated by the multinomial naive Bayes classifier on the holdout (validation classifier deliberately differs from the criterion). FST3 demo parity config.
./fst4 --config demos/demo31.cfg
demos/demo31.cfg:
data = "data/reuters_apte.arff"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
criterion = "multinom-bhattacharyya"
search = "bif"
target-d = 500
validate = "multinom"
demo32t — Example 32t: Threaded individual ranking (BIF) with SVM wrapper in very high-dimensional feature selectionFST3 parity · threaded · long-running
SVM wrapper (LINEAR kernel) + BIF individual ranking of the top 500 features with 2 evaluation threads on the 10k-feature reuters text data (single random 50/40 split, 3-fold CV criterion estimation), final SVM validation on the holdout. NOTE: compute-bound — 10105 SVM wrapper evaluations make this run for hours; LINEAR kernel may freeze LibSVM training on some data (see Known Issues). FST3 demo parity config.
./fst4 --config demos/demo32t.cfg
demos/demo32t.cfg:
data = "data/reuters_apte.arff"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-svm"
svm-kernel = "linear"
search = "bif"
target-d = 500
validate = "same"
threads = 2
demo33 — Example 33: Oscillating Search in very high-dimensional feature selectionFST3 parity · long-running
Multinomial Bhattacharyya filter on the 10k-feature reuters text data (single random 50/40 split, no inner splitter): BIF individual ranking seeds the initial 500-feature subset, then Oscillating Search (delta=1) refines it at d=500; validated by the multinomial naive Bayes classifier on the holdout. NOTE: long-running (the golden scenario runs in the slow tier). FST3 demo parity config.
./fst4 --config demos/demo33.cfg
demos/demo33.cfg:
data = "data/reuters_apte.arff"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
criterion = "multinom-bhattacharyya"
search2 = "bif"
search = "os"
os-delta = 1
target-d = 500
validate = "multinom"
demo33t — Example 33t: Threaded Oscillating Search in very high-dimensional feature selectionFST3 parity · threaded · long-running
The demo33 protocol with 8 evaluation threads: multinomial Bhattacharyya filter on the 10k-feature reuters text data (single random 50/40 split), BIF ranking seeds the initial 500-feature subset, Oscillating Search (delta=1) refines it at d=500; validated by the multinomial naive Bayes classifier on the holdout. NOTE: long-running. FST3 demo parity config.
./fst4 --config demos/demo33t.cfg
demos/demo33t.cfg:
data = "data/reuters_apte.arff"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
criterion = "multinom-bhattacharyya"
search2 = "bif"
search = "os"
os-delta = 1
target-d = 500
validate = "multinom"
threads = 8
demo34 — Example 34: Dependency-Aware Feature Ranking (DAF0)FST3 parity · long-running
Legacy-generation DAF on 5000-feature gisette data scaled to [0,1] (single random 50/50 split, 3-fold CV criterion estimation): Monte Carlo probes of cardinality 5..200 with a 1-NN wrapper feed the feature-stats tracker for 6 hours (wall-clock budget, no trial limit); the DAF0 ranking then builds the top-200 subset incrementally with kNN validation after every added feature. NOTE: 6-hour wall-clock budget by design; results are load-dependent. FST3 demo parity config.
./fst4 --config demos/demo34.cfg
demos/demo34.cfg:
data = "data/gisette_valid_nips_5000.trn"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 50
splitter2 = "cv"
splitter2-cv-folds = 3
scaler = "to01"
criterion = "wrapper-knn"
knn-k = 1
search = "montecarlo"
mc-trials = 0
mc-seconds = 21600
mc-card-min = 5
mc-card-max = 200
tracker = "feature-stats"
daf-rank = 0
daf-count = 200
daf-validate-every = 1
validate = "knn"
demo35t — Example 35t: Dependency-Aware Feature Ranking (DAF1) to enable Wrapper based FS on very-high-dimensional dataFST3 parity · threaded
Legacy-generation DAF on the 10k-feature reuters text data with whitening normalization (resubstitution outer, leave-one-out inner splitting): threaded (4 threads) Monte Carlo probes of cardinality 5..50 with an SVM wrapper (RBF kernel, parameters grid-optimized pre-search) feed the feature-stats tracker for 300 seconds; the DAF1 ranking then builds the top-1000 subset incrementally with SVM validation every 50th added feature. NOTE: wall-clock budget — results are load-dependent; SVM on reuters is heavy. FST3 demo parity config.
./fst4 --config demos/demo35t.cfg
demos/demo35t.cfg:
data = "data/reuters_apte.arff"
splitter = "resub"
splitter2 = "leave1out"
scaler = "white"
criterion = "wrapper-svm"
svm-kernel = "rbf"
svm-optimize = "pre"
search = "montecarlo"
mc-trials = 0
mc-seconds = 300
mc-card-min = 5
mc-card-max = 50
tracker = "feature-stats"
daf-rank = 1
daf-count = 1000
daf-validate-every = 50
validate = "same"
threads = 4
demo36 — FST4 4.1 demo: Budgeted stochastic (sampled) sequential search on very-high-dimensional dataFST4-native · long-running
(A new FST4-native demo, NOT an FST3 parity config: no public FST3 demo used this number.) The stochastic-floating-search paper's gisette protocol (arXiv:2608.01502; its featured campaign arm): 1-NN wrapper on the 5000-feature gisette data scaled to [0,1] (single random 50/50 split, 3-fold CV criterion estimation) + SFFS with the SAMPLED step evaluator — forward steps evaluate only 100 candidates proposed by softmax over online per-feature z-contrast statistics (exploration floor 0.2, automatic temperature, averaging horizon 100), backward steps are budgeted at 50, and the statistics are warm-started by 1000 random probes of cardinality 25. Target subset size 300 (one of the paper's larger reported sizes); sffs-delta 20 bounds the floating frontier at d=320 — the paper campaign's harvest bound — instead of the classic full frontier to d=5000; final kNN validation on the holdout. Per-step cost is bounded by the candidate budget independent of the 5000-feature dimensionality — full floating search is infeasible on this data. NOTE: long-running (hours to reach d=320).
./fst4 --config demos/demo36.cfg
demos/demo36.cfg:
data = "data/gisette_valid_nips_5000.trn"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 50
splitter2 = "cv"
splitter2-cv-folds = 3
scaler = "to01"
criterion = "wrapper-knn"
knn-k = 1
knn-distance = "L2"
search = "sffs"
target-d = 300
sffs-delta = 20
evaluator = "sampled"
step-cap = 100
step-cap-backward = 50
step-explore = 0.2
step-tau = 0
step-decay = 100
step-sampler = "softmax"
step-stats = "zcontrast"
warmup-probes = 1000
warmup-card = 25
validate = "same"
demo37t — FST4 4.1 demo: Threaded budgeted stochastic (sampled) sequential search in extreme dimensionalityFST4-native · threaded
(A new FST4-native demo, NOT an FST3 parity config: no public FST3 demo used this number. Suffix 't' = threaded, per the FST3 naming convention.) The stochastic-floating-search paper's reuters extreme-d protocol (arXiv:2608.01502): multinomial Bhattacharyya filter on the 10,105-feature reuters text data (single random 50/40 split; the filter criterion runs directly on the depth-0 train part, demo31/33 data conventions) + SFFS at target d=500 with the SAMPLED step evaluator (forward cap 100, backward cap 50, softmax proposals with exploration floor 0.2, z-contrast statistics, warm-started by 2000 random probes of cardinality 25), criterion evaluations fanned out to 8 worker threads; sffs-delta 20 bounds the floating frontier at d=520 (the campaign used an equivalent external kill at its d=500 harvest bound) instead of the classic full frontier to d=10105; validated by the multinomial naive Bayes classifier on the holdout. The threaded sampled evaluator is BIT-IDENTICAL to --threads 1 at matched --seed for any thread count: proposals ride the master RNG stream and results replay in proposal order (see "Reproducibility" in doc/FST4_CLI.md). Runtime: minutes — the budgeted step makes d=500 on 10k features tractable where full floating search is not.
./fst4 --config demos/demo37t.cfg
demos/demo37t.cfg:
data = "data/reuters_apte.arff"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
scaler = "void"
criterion = "multinom-bhattacharyya"
search = "sffs"
target-d = 500
sffs-delta = 20
evaluator = "sampled"
step-cap = 100
step-cap-backward = 50
step-explore = 0.2
step-tau = 0
step-decay = 100
step-sampler = "softmax"
step-stats = "zcontrast"
warmup-probes = 2000
warmup-card = 25
validate = "multinom"
threads = 8
demo38 — FST4 4.2 demo: Linear SVM Wrapper Feature Selection (no LibSVM needed)FST4-native
(A new FST4 demo number — no public FST3 demo used it.) The 4.2 dependency-free linear SVM as a wrapper criterion: L2-regularized squared-hinge SVM trained by dual coordinate descent (the Hsieh et al. 2008 method, implemented from scratch) on internally standardized features. The coordinate order is fixed cyclic — no RNG anywhere, so results are byte-identical at any --seed and --threads. This also retires the long-documented LibSVM LINEAR-kernel freeze for linear-SVM selection: no external library is involved at all. Same spambase protocol as demo18, so the linear margin model contrasts directly with the Random Forest (linear decision boundaries vs. axis-aligned ensembles on word-frequency features). Tune with linsvm-c / linsvm-loss (l1|l2) / linsvm-maxiter / linsvm-tol; all 4.2 wrapper metrics apply (e.g. wrapper-metric = "auc"). This demo reads data/spambase_57.csv — the CSV conversion of spambase_57.trn (identical values and sample order) — demonstrating the CSV loader on real data; the results are identical to the TRN version.
./fst4 --config demos/demo38.cfg
demos/demo38.cfg:
data = "data/spambase_57.csv"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-linsvm"
search = "sfs"
target-d = 10
validate = "same"
threads = 4
Optimal search (demo4x)
Guaranteed-optimal subset selection: exhaustive search and the four Branch & Bound variants on monotonic filter criteria.
demo40 — Example 40: Exhaustive (optimal) feature selectionFST3 parity · long-running
3-NN wrapper (Lp distance, p=3/2) + exhaustive search over all C(30,5) = 142,506 subsets of size 5 on WDBC data (50/50 split, 3-fold CV criterion estimation); a dupless tracker (capacity 50000, inclusion margin 0.05) records near-optimal alternatives, the 10 best are reported; final kNN validation on the holdout. NOTE: long-running (minutes; the golden scenario runs in the slow tier). FST3 demo parity config IN PROTOCOL, with one forced deviation: the FST3 demo ran exhaustive search over ALL subset sizes of the 15-feature speech data, which is no longer distributed; on the 30-feature WDBC replacement the full 2^30 enumeration is infeasible, so the search is bounded to target-d = 5.
./fst4 --config demos/demo40.cfg
demos/demo40.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
knn-distance = "Lp"
search = "exhaustive"
target-d = 5
tracker = "dupless"
tracker-capacity = 50000
tracker-margin = 0.05
top-k = 10
validate = "knn"
demo40t — Example 40t: Threaded Exhaustive (optimal) feature selectionFST3 parity · threaded · long-running
The demo40 protocol with 16 evaluation threads: 3-NN wrapper (Lp distance, p=3/2) + exhaustive search over all C(30,5) = 142,506 subsets of size 5 on WDBC data (50/50 split, 3-fold CV criterion estimation); dupless tracker (capacity 50000, margin 0.05) records near-optimal alternatives, the 10 best are reported; final kNN validation on the holdout. Results are bit-identical to the sequential demo40. NOTE: long-running (minutes even at 16 threads; the golden scenario of the sequential form runs in the slow tier). FST3 demo parity config IN PROTOCOL, with the same forced deviation as demo40.cfg: exhaustive search bounded to target-d = 5 (the FST3 all-sizes enumeration of the 15-feature speech data is infeasible on the 30-feature WDBC replacement).
./fst4 --config demos/demo40t.cfg
demos/demo40t.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
knn-distance = "Lp"
search = "exhaustive"
target-d = 5
tracker = "dupless"
tracker-capacity = 50000
tracker-margin = 0.05
top-k = 10
validate = "knn"
threads = 16
demo41 — Example 41: Improved Branch and Bound (IBB) optimal feature selectionFST3 parity
Bhattacharyya filter + Improved Branch & Bound at target d=10 on wdbc data (50/50 split, no inner splitter); a dupless tracker (capacity 50000, inclusion margin 0.05) records near-optimal alternatives, the 10 best are reported; validated by 3-NN (Lp distance, p=3/2) on the holdout. FST3 demo parity config.
./fst4 --config demos/demo41.cfg
demos/demo41.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
criterion = "bhattacharyya"
search = "bb-improved"
target-d = 10
tracker = "dupless"
tracker-capacity = 50000
tracker-margin = 0.05
top-k = 10
knn-distance = "Lp"
validate = "knn"
demo42 — Example 42: Branch and Bound with Partial Prediction (BBPP) optimal feature selectionFST3 parity
Bhattacharyya filter + BBPP (averaging predictor) at target d=10 on wdbc data (50/50 split, no inner splitter); a dupless tracker (capacity 50000, inclusion margin 0.05) records near-optimal alternatives, the 10 best are reported; validated by 3-NN (Lp distance, p=3/2) on the holdout. FST3 demo parity config.
./fst4 --config demos/demo42.cfg
demos/demo42.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
criterion = "bhattacharyya"
search = "bb-bbpp"
target-d = 10
tracker = "dupless"
tracker-capacity = 50000
tracker-margin = 0.05
top-k = 10
knn-distance = "Lp"
validate = "knn"
demo43 — Example 43: Fast Branch and Bound (FBB) optimal feature selectionFST3 parity
Bhattacharyya filter + Fast Branch & Bound (averaging predictor; default gamma=1.0, delta=1 as in the demo) at target d=10 on wdbc data (50/50 split, no inner splitter); a dupless tracker (capacity 50000, inclusion margin 0.05) records near-optimal alternatives, the 10 best are reported; validated by 3-NN (Lp distance, p=3/2) on the holdout. FST3 demo parity config.
./fst4 --config demos/demo43.cfg
demos/demo43.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
criterion = "bhattacharyya"
search = "bb-fast"
target-d = 10
tracker = "dupless"
tracker-capacity = 50000
tracker-margin = 0.05
top-k = 10
knn-distance = "Lp"
validate = "knn"
demo44 — FST4-native demo: multinomial Mutual Information term rankingFST4-native
The multinom-mi criterion (individual MI; a subset evaluates to the SUM of its per-feature MI values) + BIF ranking of the top 500 features on the 10k-feature reuters text data — deliberately the exact demo31 protocol with MI in place of the multinomial Bhattacharyya, so the two term-goodness rankings compare one flag for one flag. MI(f) = sum_c P(c)·theta(f|c)·log(theta(f|c)/P(f)) with P(f) = sum_c P(c)·theta(f|c) is each term's share of the mutual information between term occurrence and class under the multinomial model (P(c) = the class's share of the total term length; every share is non-negative). On this data the two criteria rank largely the same top terms; MI weights a term by how much of the corpus it accounts for, Bhattacharyya by how differently the classes use it. NOT an FST3 parity config (no public FST3 demo ever used this number).
./fst4 --config demos/demo44.cfg
demos/demo44.cfg:
data = "data/reuters_apte.arff"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
criterion = "multinom-mi"
search = "bif"
target-d = 500
validate = "multinom"
Anti-overfitting techniques (demo5x)
Result regularization, stability evaluation over repeated splits, cross-scenario similarity, bias estimation, and criteria ensembles as overfitting countermeasures.
demo50 — Example 50: Voting ensemble of criteriaFST3 parity · long-running
SFS in d-optimizing mode on spambase data (50/50 split, 3-fold CV criterion estimation) with the ensemble step evaluator: kNN wrappers with k=1/5/9 vote on every candidate, the primary criterion (reported values) is the 3-NN wrapper; final kNN validation on the holdout. NOTE: long-running (the golden scenario runs in the slow tier). Every evaluator accepts --threads N with results bit-identical to sequential - add threads = 4 below to cut the wall time roughly in half. FST3 demo parity config.
./fst4 --config demos/demo50.cfg
demos/demo50.cfg:
data = "data/spambase_57.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
search = "sfs"
evaluator = "ensemble"
ensemble-knn-ks = "1,5,9"
validate = "same"
demo51 — Example 51: (DOS) Result regularization using secondary criterionFST3 parity
3-NN wrapper + Dynamic Oscillating Search (delta=3, d-optimizing) on waveform data (50/50 split, 3-fold CV criterion estimation); the regularizer tracker records EVERY evaluated candidate, then for each margin 0.001..0.009 the smallest subset within margin of the best criterion value is reported (secondary criterion: negated subset size) and kNN-validated on the holdout. FST3 demo parity config.
./fst4 --config demos/demo51.cfg
demos/demo51.cfg:
data = "data/waveform_40.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
search = "dos"
dos-delta = 3
tracker = "regularizer"
regularize-by = "subsetsize"
regularize-margins = "0.001,0.002,0.003,0.004,0.005,0.006,0.007,0.008,0.009"
validate = "same"
demo52t — Example 52t: (Threaded SFRS) Result regularization using secondary criterionFST3 parity · C++ exemplar ships · threaded · long-running
3-NN wrapper + Sequential Forward Retreating Search with 2 evaluation threads on waveform data (50/50 split, 3-fold CV criterion estimation); the regularizer tracker records EVERY evaluated candidate, then for each margin 0.001..0.009 the smallest subset within margin of the best criterion value is reported (secondary criterion: negated subset size) and kNN-validated on the holdout. NOTE: long-running (about ten minutes; the golden scenario runs in the slow tier). FST3 demo parity config; the compiled exemplar demo52t.cpp still ships and implements the same protocol.
./fst4 --config demos/demo52t.cfg
demos/demo52t.cfg:
data = "data/waveform_40.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
search = "sfrs"
tracker = "regularizer"
regularize-by = "subsetsize"
regularize-margins = "0.001,0.002,0.003,0.004,0.005,0.006,0.007,0.008,0.009"
validate = "same"
threads = 2
demo52t.cpp — the compiled C++ exemplar in the API reference →
demo53 — Example 53: Hybrid feature selectionFST3 parity
SVM wrapper (default RBF kernel) + SBS (sequential BACKWARD selection, d-optimizing) on WDBC data scaled to [0,1] (single random 50/40 split, 3-fold CV criterion estimation) with the hybrid step evaluator: a Bhattacharyya prefilter (initialized on the whole depth-0 train part) pre-orders candidates and only the best 50% reach the SVM wrapper; final SVM validation on the holdout. FST3 demo parity config.
./fst4 --config demos/demo53.cfg
demos/demo53.cfg:
data = "data/wdbc_30.trn"
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
splitter2 = "cv"
splitter2-cv-folds = 3
scaler = "to01"
criterion = "wrapper-svm"
search = "sbs"
evaluator = "hybrid"
hybrid-prefilter = "bhattacharyya"
hybrid-keep-perc = 50
validate = "same"
demo54 — Example 54: Feature Selection Stability EvaluationFST3 parity
3-NN wrapper + SFS in d-optimizing mode, run once per each of 10 random 80/20 splits of WDBC data (3-fold CV criterion estimation per trial); the stability-evaluator tracker collects per-trial results and reports criterion value / subset size means and stddevs plus the stability measures (CWrel/ATI/CW/ANHI/SH/PH/C). FST3 demo parity config.
./fst4 --config demos/demo54.cfg
demos/demo54.cfg:
data = "data/wdbc_30.trn"
splitter = "randrand"
rr-splits = 10
rr-train = 80
rr-test = 20
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
search = "sfs"
repeat-over-splits = true
tracker = "stabileval"
demo55 — Example 55: Evaluating Similarity of Two Feature Selection ProcessesFST3 parity · C++ exemplar ships
Two feature-selection scenarios run over the SAME 10 random 95/5 splits of WDBC data and are compared by cross-scenario tracker similarity (IATI/ICW/IANHI). Scenario A (this file): 3-NN wrapper with L1 distance + DOS (delta=10, d-optimizing). Scenario B (tests/fst4_compare_demo55_b.cfg): normal Bhattacharyya filter + SFFS at target d=7, re-initialized per split. Both use 3-fold CV criterion estimation and the stability-evaluator tracker. FST3 demo parity config; the compiled exemplar demo55.cpp still ships and implements the same protocol.
./fst4 --config demos/demo55.cfg
demos/demo55.cfg:
data = "data/wdbc_30.trn"
splitter = "randrand"
rr-splits = 10
rr-train = 95
rr-test = 5
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
knn-distance = "L1"
search = "dos"
dos-delta = 10
repeat-over-splits = true
tracker = "stabileval"
compare-config = "tests/fst4_compare_demo55_b.cfg"
demo55.cpp — the compiled C++ exemplar in the API reference →
demo56 — Example 56: Revealing feature selection results' biasFST3 parity
3-NN wrapper + Dynamic Oscillating Search (delta=1, d-optimizing) on sonar data (50/50 split, 3-fold CV criterion estimation); after the search the wrapper's bias (train-vs-test optimism) is estimated on the selected subset at splitting depth 1, and the result is kNN-validated on the holdout. FST3 demo parity config.
./fst4 --config demos/demo56.cfg
demos/demo56.cfg:
data = "data/sonar_60.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
search = "dos"
dos-delta = 1
bias-estimate = true
validate = "same"
Complementary scenarios (demo6x)
Supporting workflows: feature acquisition cost, class-cost weighting, missing data, sample classification, and the external-classifier bridge.
demo60 — Example 60: Detecting alternative feature selection results with equal criterion valueFST3 parity · long-running
3-NN wrapper + Dynamic Oscillating Search (delta=3, d-optimizing) on optdigits (50/50 split, 3-fold CV criterion estimation); the dupless tracker is attached to the EVALUATOR so every evaluated candidate is offered to it (inclusion margin 0.05) — equal-value alternative subsets show up in the top-10 report; final kNN validation on the holdout. With no tracker-capacity key the dupless tracker keeps the top-k (10) best rather than every candidate as the FST3 demo did — result-neutral for this protocol, since the report prints the top 10 either way. NOTE: long-running (the golden scenario runs in the slow tier). FST3 demo parity config.
./fst4 --config demos/demo60.cfg
demos/demo60.cfg:
data = "data/optdigits_64.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
search = "dos"
dos-delta = 3
tracker = "dupless"
tracker-margin = 0.05
tracker-attach = "evaluator"
top-k = 10
validate = "knn"
demo61 — Example 61: Feature selection that respects pre-specified feature weightsFST3 parity
3-NN wrapper + SFFS in d-optimizing mode on WDBC data (50/50 split, 3-fold CV criterion estimation); the regularizer tracker records EVERY evaluated candidate, then for each margin 0..0.045 the cheapest subset within margin of the best criterion value is reported (secondary criterion: negated sum of the per-feature acquisition costs below) and kNN-validated on the holdout. The costs are illustrative (as in the FST3 demo): the first 15 are the FST3 demo61 values, extended to WDBC's 30 features in the same spirit. FST3 demo parity config.
./fst4 --config demos/demo61.cfg
demos/demo61.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
search = "sffs"
tracker = "regularizer"
regularize-by = "weights"
feature-costs = "1,1.2,1,1.3,1.02,2.4,3.9,1.2,7.1,22,9.52,1.08,3.27,1.44,1.04,2.1,1.15,5.6,1.02,3.4,12,1.33,2.05,1.1,8.4,1.7,4.2,1.06,2.9,6.3"
regularize-margins = "0,0.005,0.01,0.015,0.02,0.025,0.03,0.035,0.04,0.045"
validate = "same"
demo62 — Example 62: (Missing data substitution) Combined feature subset contents, size and SVM parameters optimizationFST3 parity
The demo23 protocol on sonar data with missing values: the exact value 5 is treated as a missing-data code and substituted by the per-feature training average. SVM wrapper (RBF kernel) + Dynamic Oscillating Search (delta=3, d-optimizing; single random 50/40 split, 3-fold CV criterion estimation); alternating SVM parameter optimization and search while the train criterion improves, best parameters restored before the final SVM validation. FST3 demo parity config.
./fst4 --config demos/demo62.cfg
demos/demo62.cfg:
data = "data/sonar_60_missing_data.trn"
missing-value = 5
splitter = "randrand"
rr-splits = 1
rr-train = 50
rr-test = 40
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-svm"
svm-kernel = "rbf"
svm-optimize = "alternating"
search = "dos"
dos-delta = 3
validate = "same"
demo63 — Example 63: Classification of new data samples on the selected subspaceFST3 parity
3-NN wrapper + SFFS in d-optimizing mode on WDBC data (50/50 split, 3-fold CV criterion estimation), final kNN validation on the holdout; afterwards the classifier is trained on the depth-0 train part and classifies the new full-length sample vectors listed in tests/demo63_samples.txt (the demo's two hardcoded samples), printing the predicted class per row. FST3 demo parity config.
./fst4 --config demos/demo63.cfg
demos/demo63.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-knn"
knn-k = 3
search = "sffs"
validate = "same"
classify-samples = "tests/demo63_samples.txt"
demo64 — FST4 4.2 demo: External-Classifier Bridge (bring your own model)FST4-native
(A new FST4 demo number — no demo64 existed in FST3; it sits in the demo6x complementary group, where an integration scenario belongs topically.) Feature selection wrapped around a classifier THAT IS NOT PART OF FST4: the wrapper-extern criterion launches the extern-cmd command once (a persistent child process per criterion clone) and drives it through a line protocol — "TRAIN <N> <d> <K>" + N labeled rows, answered by "OK", then "TEST <M> <d>" + M rows, answered by M predicted class indices, repeated for every candidate subset. The command here is the shipped reference implementation, a nearest-centroid classifier in awk (tests/extern_centroid.awk) — swap in any scikit-learn/R/Julia model behind the same three-message protocol. TWO LOUD CAVEATS (see doc/FST4_CLI.md): the command is USER-SUPPLIED CODE EXECUTION (treat configs with extern-cmd like scripts), and FST4's reproducibility guarantees END AT THE BRIDGE — determinism is now the external model's responsibility. AUC is unavailable (labels-only protocol); confusion-based metrics (balanced-accuracy, f1, class-weights) work. Needs awk on PATH (any Unix; Git Bash on Windows).
./fst4 --config demos/demo64.cfg
demos/demo64.cfg:
data = "data/wdbc_30.trn"
splitter = "5050"
splitter2 = "cv"
splitter2-cv-folds = 3
criterion = "wrapper-extern"
extern-cmd = "awk -f tests/extern_centroid.awk"
search = "sfs"
target-d = 5
validate = "same"