Summary
This experiment investigates headphone eq calibration. Fractional factorial screening of bass boost, mid presence, treble roll-off, soundstage width, and crossfeed for preference score and fatigue reduction.
The design varies 5 factors: bass boost db (dB), ranging from 0 to 8, mid presence db (dB), ranging from -3 to 3, treble rolloff db (dB), ranging from -6 to 0, soundstage pct (%), ranging from 0 to 100, and crossfeed pct (%), ranging from 0 to 60. The goal is to optimize 2 responses: preference score (pts) (maximize) and fatigue score (pts) (minimize). Fixed conditions held constant across all runs include headphone = open_back, source = lossless.
A fractional factorial design reduces the number of runs from 32 to 8 by deliberately confounding higher-order interactions. This is ideal for screening — identifying which of the 5 factors matter most before investing in a full study.
Key Findings
For preference score, the most influential factors were crossfeed pct (50.0%), soundstage pct (23.5%), mid presence db (16.2%). The best observed value was 7.1 (at bass boost db = 8, mid presence db = -3, treble rolloff db = -6).
For fatigue score, the most influential factors were mid presence db (31.6%), bass boost db (22.4%), treble rolloff db (21.4%). The best observed value was 1.4 (at bass boost db = 8, mid presence db = 3, treble rolloff db = -6).
Recommended Next Steps
- Follow up with a response surface design (CCD or Box-Behnken) on the top 3–4 factors to model curvature and find the true optimum.
- Consider whether any fixed factors should be varied in a future study.
- The screening results can guide factor reduction — drop factors contributing less than 5% and re-run with a smaller, more focused design.
Experimental Setup
Factors
| Factor | Low | High | Unit |
bass_boost_db | 0 | 8 | dB |
mid_presence_db | -3 | 3 | dB |
treble_rolloff_db | -6 | 0 | dB |
soundstage_pct | 0 | 100 | % |
crossfeed_pct | 0 | 60 | % |
Fixed: headphone = open_back, source = lossless
Responses
| Response | Direction | Unit |
preference_score | ↑ maximize | pts |
fatigue_score | ↓ minimize | pts |
Configuration
{
"metadata": {
"name": "Headphone EQ Calibration",
"description": "Fractional factorial screening of bass boost, mid presence, treble roll-off, soundstage width, and crossfeed for preference score and fatigue reduction"
},
"factors": [
{
"name": "bass_boost_db",
"levels": [
"0",
"8"
],
"type": "continuous",
"unit": "dB"
},
{
"name": "mid_presence_db",
"levels": [
"-3",
"3"
],
"type": "continuous",
"unit": "dB"
},
{
"name": "treble_rolloff_db",
"levels": [
"-6",
"0"
],
"type": "continuous",
"unit": "dB"
},
{
"name": "soundstage_pct",
"levels": [
"0",
"100"
],
"type": "continuous",
"unit": "%"
},
{
"name": "crossfeed_pct",
"levels": [
"0",
"60"
],
"type": "continuous",
"unit": "%"
}
],
"fixed_factors": {
"headphone": "open_back",
"source": "lossless"
},
"responses": [
{
"name": "preference_score",
"optimize": "maximize",
"unit": "pts"
},
{
"name": "fatigue_score",
"optimize": "minimize",
"unit": "pts"
}
],
"settings": {
"operation": "fractional_factorial",
"test_script": "use_cases/164_headphone_eq/sim.sh"
}
}
Experimental Matrix
The Fractional Factorial Design produces 8 runs. Each row is one experiment with specific factor settings.
| Run | bass_boost_db | mid_presence_db | treble_rolloff_db | soundstage_pct | crossfeed_pct |
| 1 | 0 | 3 | 0 | 0 | 0 |
| 2 | 8 | -3 | -6 | 0 | 0 |
| 3 | 8 | 3 | -6 | 100 | 0 |
| 4 | 8 | 3 | 0 | 100 | 60 |
| 5 | 0 | 3 | -6 | 0 | 60 |
| 6 | 8 | -3 | 0 | 0 | 60 |
| 7 | 0 | -3 | -6 | 100 | 60 |
| 8 | 0 | -3 | 0 | 100 | 0 |
Step-by-Step Workflow
1
Preview the design
$ doe info --config use_cases/164_headphone_eq/config.json
2
Generate the runner script
$ doe generate --config use_cases/164_headphone_eq/config.json \
--output use_cases/164_headphone_eq/results/run.sh --seed 42
3
Execute the experiments
$ bash use_cases/164_headphone_eq/results/run.sh
4
Analyze results
$ doe analyze --config use_cases/164_headphone_eq/config.json
5
Get optimization recommendations
$ doe optimize --config use_cases/164_headphone_eq/config.json
6
Multi-objective optimization
With 2 competing responses, use --multi to find the best compromise via Derringer–Suich desirability.
$ doe optimize --config use_cases/164_headphone_eq/config.json --multi
7
Generate the HTML report
$ doe report --config use_cases/164_headphone_eq/config.json \
--output use_cases/164_headphone_eq/results/report.html
Features Exercised
| Feature | Value |
| Design type | fractional_factorial |
| Factor types | continuous (all 5) |
| Arg style | double-dash |
| Responses | 2 (preference_score ↑, fatigue_score ↓) |
| Total runs | 8 |
Analysis Results
Generated from actual experiment runs using the DOE Helper Tool.
Response: preference_score
Top factors: crossfeed_pct (50.0%), soundstage_pct (23.5%), mid_presence_db (16.2%).
ANOVA
| Source | DF | SS | MS | F | p-value |
| Source | DF | SS | MS | F | p-value |
| bass_boost_db | 1 | 0.0800 | 0.0800 | 0.088 | 0.7785 |
| mid_presence_db | 1 | 0.6050 | 0.6050 | 0.667 | 0.4513 |
| treble_rolloff_db | 1 | 0.0450 | 0.0450 | 0.050 | 0.8326 |
| soundstage_pct | 1 | 1.2800 | 1.2800 | 1.410 | 0.2883 |
| crossfeed_pct | 1 | 5.7800 | 5.7800 | 6.369 | 0.0529 |
| bass_boost_db*mid_presence_db | 1 | 1.2800 | 1.2800 | 1.410 | 0.2883 |
| bass_boost_db*treble_rolloff_db | 1 | 5.7800 | 5.7800 | 6.369 | 0.0529 |
| bass_boost_db*soundstage_pct | 1 | 0.6050 | 0.6050 | 0.667 | 0.4513 |
| bass_boost_db*crossfeed_pct | 1 | 0.0450 | 0.0450 | 0.050 | 0.8326 |
| mid_presence_db*treble_rolloff_db | 1 | 2.2050 | 2.2050 | 2.430 | 0.1798 |
| mid_presence_db*soundstage_pct | 1 | 0.0800 | 0.0800 | 0.088 | 0.7785 |
| mid_presence_db*crossfeed_pct | 1 | 0.9800 | 0.9800 | 1.080 | 0.3463 |
| treble_rolloff_db*soundstage_pct | 1 | 0.9800 | 0.9800 | 1.080 | 0.3463 |
| treble_rolloff_db*crossfeed_pct | 1 | 0.0800 | 0.0800 | 0.088 | 0.7785 |
| soundstage_pct*crossfeed_pct | 1 | 2.2050 | 2.2050 | 2.430 | 0.1798 |
| Error | (Lenth | PSE) | 5 | 4.5375 | 0.9075 |
| Total | 7 | 10.9750 | 1.5679 | | |
Pareto Chart
Main Effects Plot
Normal Probability Plot of Effects
Half-Normal Plot of Effects
Model Diagnostics
Response: fatigue_score
Top factors: mid_presence_db (31.6%), bass_boost_db (22.4%), treble_rolloff_db (21.4%).
ANOVA
| Source | DF | SS | MS | F | p-value |
| Source | DF | SS | MS | F | p-value |
| bass_boost_db | 1 | 2.4200 | 2.4200 | 0.732 | 0.4314 |
| mid_presence_db | 1 | 4.8050 | 4.8050 | 1.453 | 0.2820 |
| treble_rolloff_db | 1 | 2.2050 | 2.2050 | 0.667 | 0.4513 |
| soundstage_pct | 1 | 1.1250 | 1.1250 | 0.340 | 0.5851 |
| crossfeed_pct | 1 | 0.4050 | 0.4050 | 0.122 | 0.7407 |
| bass_boost_db*mid_presence_db | 1 | 1.1250 | 1.1250 | 0.340 | 0.5851 |
| bass_boost_db*treble_rolloff_db | 1 | 0.4050 | 0.4050 | 0.122 | 0.7407 |
| bass_boost_db*soundstage_pct | 1 | 4.8050 | 4.8050 | 1.453 | 0.2820 |
| bass_boost_db*crossfeed_pct | 1 | 2.2050 | 2.2050 | 0.667 | 0.4513 |
| mid_presence_db*treble_rolloff_db | 1 | 7.2200 | 7.2200 | 2.183 | 0.1996 |
| mid_presence_db*soundstage_pct | 1 | 2.4200 | 2.4200 | 0.732 | 0.4314 |
| mid_presence_db*crossfeed_pct | 1 | 0.7200 | 0.7200 | 0.218 | 0.6604 |
| treble_rolloff_db*soundstage_pct | 1 | 0.7200 | 0.7200 | 0.218 | 0.6604 |
| treble_rolloff_db*crossfeed_pct | 1 | 2.4200 | 2.4200 | 0.732 | 0.4314 |
| soundstage_pct*crossfeed_pct | 1 | 7.2200 | 7.2200 | 2.183 | 0.1996 |
| Error | (Lenth | PSE) | 5 | 16.5375 | 3.3075 |
| Total | 7 | 18.9000 | 2.7000 | | |
Pareto Chart
Main Effects Plot
Normal Probability Plot of Effects
Half-Normal Plot of Effects
Model Diagnostics
Response Surface Plots
3D surfaces fitted with quadratic RSM. Red dots are observed data points.
fatigue score bass boost db vs crossfeed pct
fatigue score bass boost db vs mid presence db
fatigue score bass boost db vs soundstage pct
fatigue score bass boost db vs treble rolloff db
fatigue score mid presence db vs crossfeed pct
fatigue score mid presence db vs soundstage pct
fatigue score mid presence db vs treble rolloff db
fatigue score soundstage pct vs crossfeed pct
fatigue score treble rolloff db vs crossfeed pct
fatigue score treble rolloff db vs soundstage pct
preference score bass boost db vs crossfeed pct
preference score bass boost db vs mid presence db
preference score bass boost db vs soundstage pct
preference score bass boost db vs treble rolloff db
preference score mid presence db vs crossfeed pct
preference score mid presence db vs soundstage pct
preference score mid presence db vs treble rolloff db
preference score soundstage pct vs crossfeed pct
preference score treble rolloff db vs crossfeed pct
preference score treble rolloff db vs soundstage pct
Multi-Objective Optimization
When responses compete, Derringer–Suich desirability finds the best compromise.
Each response is scaled to a 0–1 desirability, then combined via a weighted geometric mean.
Overall Desirability
D = 0.7037
Per-Response Desirability
| Response | Weight | Desirability | Predicted | Dir |
preference_score |
1.5 |
|
7.00 0.9293 7.00 pts |
↑ |
fatigue_score |
1.0 |
|
4.10 0.4636 4.10 pts |
↓ |
Recommended Settings
| Factor | Value |
bass_boost_db | 8 dB |
mid_presence_db | 3 dB |
treble_rolloff_db | 0 dB |
soundstage_pct | 100 % |
crossfeed_pct | 60 % |
Source: from observed run #3
Trade-off Summary
Sacrifice = how much worse than single-objective best.
| Response | Predicted | Best Observed | Sacrifice |
fatigue_score | 4.10 | 1.40 | +2.70 |
Top 3 Runs by Desirability
| Run | D | Factor Settings |
| #7 | 0.6075 | bass_boost_db=8, mid_presence_db=-3, treble_rolloff_db=-6, soundstage_pct=0, crossfeed_pct=0 |
| #2 | 0.5211 | bass_boost_db=0, mid_presence_db=-3, treble_rolloff_db=-6, soundstage_pct=100, crossfeed_pct=60 |
Model Quality
| Response | R² | Type |
fatigue_score | 0.5757 | linear |
Full Multi-Objective Output
============================================================
MULTI-OBJECTIVE OPTIMIZATION
Method: Derringer-Suich Desirability Function
============================================================
Overall desirability: D = 0.7037
Response Weight Desirability Predicted Direction
---------------------------------------------------------------------
preference_score 1.5 0.9293 7.00 pts ↑
fatigue_score 1.0 0.4636 4.10 pts ↓
Recommended settings:
bass_boost_db = 8 dB
mid_presence_db = 3 dB
treble_rolloff_db = 0 dB
soundstage_pct = 100 %
crossfeed_pct = 60 %
(from observed run #3)
Trade-off summary:
preference_score: 7.00 (best observed: 7.10, sacrifice: +0.10)
fatigue_score: 4.10 (best observed: 1.40, sacrifice: +2.70)
Model quality:
preference_score: R² = 0.5317 (linear)
fatigue_score: R² = 0.5757 (linear)
Top 3 observed runs by overall desirability:
1. Run #3 (D=0.7037): bass_boost_db=8, mid_presence_db=3, treble_rolloff_db=0, soundstage_pct=100, crossfeed_pct=60
2. Run #7 (D=0.6075): bass_boost_db=8, mid_presence_db=-3, treble_rolloff_db=-6, soundstage_pct=0, crossfeed_pct=0
3. Run #2 (D=0.5211): bass_boost_db=0, mid_presence_db=-3, treble_rolloff_db=-6, soundstage_pct=100, crossfeed_pct=60
Full Analysis Output
=== Main Effects: preference_score ===
Factor Effect Std Error % Contribution
--------------------------------------------------------------
crossfeed_pct 1.7000 0.4427 50.0%
soundstage_pct 0.8000 0.4427 23.5%
mid_presence_db -0.5500 0.4427 16.2%
bass_boost_db -0.2000 0.4427 5.9%
treble_rolloff_db 0.1500 0.4427 4.4%
=== ANOVA Table: preference_score ===
Source DF SS MS F p-value
-----------------------------------------------------------------------------
bass_boost_db 1 0.0800 0.0800 0.088 0.7785
mid_presence_db 1 0.6050 0.6050 0.667 0.4513
treble_rolloff_db 1 0.0450 0.0450 0.050 0.8326
soundstage_pct 1 1.2800 1.2800 1.410 0.2883
crossfeed_pct 1 5.7800 5.7800 6.369 0.0529
bass_boost_db*mid_presence_db 1 1.2800 1.2800 1.410 0.2883
bass_boost_db*treble_rolloff_db 1 5.7800 5.7800 6.369 0.0529
bass_boost_db*soundstage_pct 1 0.6050 0.6050 0.667 0.4513
bass_boost_db*crossfeed_pct 1 0.0450 0.0450 0.050 0.8326
mid_presence_db*treble_rolloff_db 1 2.2050 2.2050 2.430 0.1798
mid_presence_db*soundstage_pct 1 0.0800 0.0800 0.088 0.7785
mid_presence_db*crossfeed_pct 1 0.9800 0.9800 1.080 0.3463
treble_rolloff_db*soundstage_pct 1 0.9800 0.9800 1.080 0.3463
treble_rolloff_db*crossfeed_pct 1 0.0800 0.0800 0.088 0.7785
soundstage_pct*crossfeed_pct 1 2.2050 2.2050 2.430 0.1798
Error (Lenth PSE) 5 4.5375 0.9075
Total 7 10.9750 1.5679
Note: Error estimated using Lenth's pseudo-standard-error (unreplicated design)
=== Interaction Effects: preference_score ===
Factor A Factor B Interaction % Contribution
------------------------------------------------------------------------
bass_boost_db treble_rolloff_db 1.7000 23.9%
mid_presence_db treble_rolloff_db 1.0500 14.8%
soundstage_pct crossfeed_pct 1.0500 14.8%
bass_boost_db mid_presence_db 0.8000 11.3%
mid_presence_db crossfeed_pct 0.7000 9.9%
treble_rolloff_db soundstage_pct 0.7000 9.9%
bass_boost_db soundstage_pct -0.5500 7.7%
mid_presence_db soundstage_pct -0.2000 2.8%
treble_rolloff_db crossfeed_pct -0.2000 2.8%
bass_boost_db crossfeed_pct 0.1500 2.1%
=== Summary Statistics: preference_score ===
bass_boost_db:
Level N Mean Std Min Max
------------------------------------------------------------
0 4 5.3750 1.2038 4.1000 7.0000
8 4 5.1750 1.4773 3.5000 7.1000
mid_presence_db:
Level N Mean Std Min Max
------------------------------------------------------------
-3 4 5.5500 0.9678 5.0000 7.0000
3 4 5.0000 1.5875 3.5000 7.1000
treble_rolloff_db:
Level N Mean Std Min Max
------------------------------------------------------------
-6 4 5.2000 1.4353 3.5000 7.0000
0 4 5.3500 1.2583 4.1000 7.1000
soundstage_pct:
Level N Mean Std Min Max
------------------------------------------------------------
0 4 4.8750 0.5315 4.1000 5.3000
100 4 5.6750 1.7173 3.5000 7.1000
crossfeed_pct:
Level N Mean Std Min Max
------------------------------------------------------------
0 4 4.4250 0.7632 3.5000 5.1000
60 4 6.1250 1.0720 5.1000 7.1000
=== Main Effects: fatigue_score ===
Factor Effect Std Error % Contribution
--------------------------------------------------------------
mid_presence_db 1.5500 0.5809 31.6%
bass_boost_db -1.1000 0.5809 22.4%
treble_rolloff_db 1.0500 0.5809 21.4%
soundstage_pct 0.7500 0.5809 15.3%
crossfeed_pct -0.4500 0.5809 9.2%
=== ANOVA Table: fatigue_score ===
Source DF SS MS F p-value
-----------------------------------------------------------------------------
bass_boost_db 1 2.4200 2.4200 0.732 0.4314
mid_presence_db 1 4.8050 4.8050 1.453 0.2820
treble_rolloff_db 1 2.2050 2.2050 0.667 0.4513
soundstage_pct 1 1.1250 1.1250 0.340 0.5851
crossfeed_pct 1 0.4050 0.4050 0.122 0.7407
bass_boost_db*mid_presence_db 1 1.1250 1.1250 0.340 0.5851
bass_boost_db*treble_rolloff_db 1 0.4050 0.4050 0.122 0.7407
bass_boost_db*soundstage_pct 1 4.8050 4.8050 1.453 0.2820
bass_boost_db*crossfeed_pct 1 2.2050 2.2050 0.667 0.4513
mid_presence_db*treble_rolloff_db 1 7.2200 7.2200 2.183 0.1996
mid_presence_db*soundstage_pct 1 2.4200 2.4200 0.732 0.4314
mid_presence_db*crossfeed_pct 1 0.7200 0.7200 0.218 0.6604
treble_rolloff_db*soundstage_pct 1 0.7200 0.7200 0.218 0.6604
treble_rolloff_db*crossfeed_pct 1 2.4200 2.4200 0.732 0.4314
soundstage_pct*crossfeed_pct 1 7.2200 7.2200 2.183 0.1996
Error (Lenth PSE) 5 16.5375 3.3075
Total 7 18.9000 2.7000
Note: Error estimated using Lenth's pseudo-standard-error (unreplicated design)
=== Interaction Effects: fatigue_score ===
Factor A Factor B Interaction % Contribution
------------------------------------------------------------------------
mid_presence_db treble_rolloff_db 1.9000 17.3%
soundstage_pct crossfeed_pct 1.9000 17.3%
bass_boost_db soundstage_pct 1.5500 14.1%
mid_presence_db soundstage_pct -1.1000 10.0%
treble_rolloff_db crossfeed_pct -1.1000 10.0%
bass_boost_db crossfeed_pct 1.0500 9.5%
bass_boost_db mid_presence_db 0.7500 6.8%
mid_presence_db crossfeed_pct 0.6000 5.5%
treble_rolloff_db soundstage_pct 0.6000 5.5%
bass_boost_db treble_rolloff_db -0.4500 4.1%
=== Summary Statistics: fatigue_score ===
bass_boost_db:
Level N Mean Std Min Max
------------------------------------------------------------
0 4 4.6000 1.2356 3.6000 6.4000
8 4 3.5000 1.9916 1.4000 6.2000
mid_presence_db:
Level N Mean Std Min Max
------------------------------------------------------------
-3 4 3.2750 1.3226 1.4000 4.3000
3 4 4.8250 1.7173 3.1000 6.4000
treble_rolloff_db:
Level N Mean Std Min Max
------------------------------------------------------------
-6 4 3.5250 0.4349 3.1000 4.1000
0 4 4.5750 2.3186 1.4000 6.4000
soundstage_pct:
Level N Mean Std Min Max
------------------------------------------------------------
0 4 3.6750 2.0614 1.4000 6.4000
100 4 4.4250 1.2945 3.1000 6.2000
crossfeed_pct:
Level N Mean Std Min Max
------------------------------------------------------------
0 4 4.2750 1.5108 3.1000 6.4000
60 4 3.8250 1.9704 1.4000 6.2000
Optimization Recommendations
=== Optimization: preference_score ===
Direction: maximize
Best observed run: #4
bass_boost_db = 8
mid_presence_db = -3
treble_rolloff_db = -6
soundstage_pct = 0
crossfeed_pct = 0
Value: 7.1
RSM Model (linear, R² = 0.7098, Adj R² = -0.0157):
Coefficients:
intercept +5.2750
bass_boost_db -0.1000
mid_presence_db -0.4500
treble_rolloff_db -0.1250
soundstage_pct +0.3250
crossfeed_pct -0.8000
Predicted optimum (from linear model, at observed points):
bass_boost_db = 0
mid_presence_db = -3
treble_rolloff_db = 0
soundstage_pct = 100
crossfeed_pct = 0
Predicted value: 6.8250
Surface optimum (via L-BFGS-B, linear model):
bass_boost_db = 0
mid_presence_db = -3
treble_rolloff_db = -6
soundstage_pct = 100
crossfeed_pct = 0
Predicted value: 7.0750
Model quality: Good fit — general trends are captured, some noise remains.
Factor importance:
1. crossfeed_pct (effect: -1.6, contribution: 44.4%)
2. mid_presence_db (effect: -0.9, contribution: 25.0%)
3. soundstage_pct (effect: 0.7, contribution: 18.1%)
4. treble_rolloff_db (effect: -0.2, contribution: 6.9%)
5. bass_boost_db (effect: -0.2, contribution: 5.6%)
=== Optimization: fatigue_score ===
Direction: minimize
Best observed run: #7
bass_boost_db = 8
mid_presence_db = 3
treble_rolloff_db = -6
soundstage_pct = 100
crossfeed_pct = 0
Value: 1.4
RSM Model (linear, R² = 0.5799, Adj R² = -0.4704):
Coefficients:
intercept +4.0500
bass_boost_db -0.5500
mid_presence_db -0.2000
treble_rolloff_db -0.3500
soundstage_pct -0.9500
crossfeed_pct +0.0500
Predicted optimum (from linear model, at observed points):
bass_boost_db = 0
mid_presence_db = 3
treble_rolloff_db = -6
soundstage_pct = 0
crossfeed_pct = 60
Predicted value: 5.7500
Surface optimum (via L-BFGS-B, linear model):
bass_boost_db = 8
mid_presence_db = 3
treble_rolloff_db = 0
soundstage_pct = 100
crossfeed_pct = 0
Predicted value: 1.9500
Model quality: Moderate fit — use predictions directionally, not precisely.
Factor importance:
1. soundstage_pct (effect: -1.9, contribution: 45.2%)
2. bass_boost_db (effect: -1.1, contribution: 26.2%)
3. treble_rolloff_db (effect: -0.7, contribution: 16.7%)
4. mid_presence_db (effect: -0.4, contribution: 9.5%)
5. crossfeed_pct (effect: 0.1, contribution: 2.4%)