gaurv007 commited on
Commit
06c179a
·
verified ·
1 Parent(s): e49d195

Upload tests/test_fitness_and_theme.py with huggingface_hub

Browse files
Files changed (1) hide show
  1. tests/test_fitness_and_theme.py +74 -0
tests/test_fitness_and_theme.py ADDED
@@ -0,0 +1,74 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ """Tests for fitness function and theme sampler."""
2
+ import pytest
3
+ from alpha_factory.deterministic.fitness import compute_fitness, would_pass_brain, regime_tag_years
4
+ from alpha_factory.deterministic.theme_sampler import compute_gap_scores, pick_theme
5
+ from alpha_factory.schemas import BrainMetrics
6
+
7
+
8
+ class TestFitness:
9
+ def test_high_sharpe_alpha(self):
10
+ metrics = BrainMetrics(
11
+ alpha_id="test", sharpe_full=2.0, sharpe_is=2.2, sharpe_os=1.8,
12
+ fitness=1.5, turnover=0.3, returns=0.15, max_drawdown=0.03,
13
+ yearly_sharpe=[1.5, 2.0, 1.8, 2.1, 1.6], yearly_returns=[0.03]*5,
14
+ )
15
+ score = compute_fitness(metrics, max_corr_to_library=0.2, theme_novelty_score=0.8)
16
+ assert score > 1.0 # Should be a good score
17
+
18
+ def test_negative_sharpe_penalized(self):
19
+ metrics = BrainMetrics(
20
+ alpha_id="test", sharpe_full=-0.5, sharpe_is=0.5, sharpe_os=-0.5,
21
+ fitness=0.3, turnover=0.5, returns=-0.05, max_drawdown=0.15,
22
+ yearly_sharpe=[-1.0, -0.5, 0.2, -0.8, -0.3], yearly_returns=[-0.02]*5,
23
+ )
24
+ score = compute_fitness(metrics, max_corr_to_library=0.1, theme_novelty_score=0.5)
25
+ assert score < 0 # Should be negative
26
+
27
+ def test_high_correlation_penalized(self):
28
+ metrics = BrainMetrics(
29
+ alpha_id="test", sharpe_full=1.5, sharpe_is=1.6, sharpe_os=1.4,
30
+ fitness=1.2, turnover=0.25, returns=0.1, max_drawdown=0.04,
31
+ yearly_sharpe=[1.2, 1.5, 1.3, 1.4, 1.6], yearly_returns=[0.02]*5,
32
+ )
33
+ low_corr = compute_fitness(metrics, max_corr_to_library=0.1, theme_novelty_score=0.5)
34
+ high_corr = compute_fitness(metrics, max_corr_to_library=0.8, theme_novelty_score=0.5)
35
+ assert low_corr > high_corr # Lower correlation = higher score
36
+
37
+ def test_would_pass_brain(self):
38
+ good = BrainMetrics(
39
+ alpha_id="test", sharpe_full=1.5, sharpe_is=1.6, sharpe_os=1.4,
40
+ fitness=1.2, turnover=0.25, returns=0.1, max_drawdown=0.04,
41
+ yearly_sharpe=[1.2, 1.5, 1.3, 1.4, 1.6], yearly_returns=[0.02]*5,
42
+ )
43
+ result = would_pass_brain(good)
44
+ assert result["sharpe_ge_1.25"] == True
45
+ assert result["fitness_ge_1.0"] == True
46
+
47
+ def test_regime_tags(self):
48
+ yearly = [1.5, 2.0, -0.5, 1.8, 1.2]
49
+ tags = regime_tag_years(yearly)
50
+ assert tags["2019"] == "moderate"
51
+ assert tags["2021"] == "negative"
52
+
53
+
54
+ class TestThemeSampler:
55
+ def test_unexplored_themes_rank_higher(self):
56
+ existing = ["momentum", "momentum", "momentum", "value", "value"]
57
+ tags = ["momentum", "momentum", "momentum", "value", "value"]
58
+ scores = compute_gap_scores(existing, tags)
59
+ # Themes with 0 alphas should rank highest
60
+ top_theme = scores[0][0]
61
+ assert top_theme not in ["momentum", "value"]
62
+
63
+ def test_dead_themes_excluded(self):
64
+ existing = ["momentum"]
65
+ tags = ["momentum"]
66
+ dead = ["option_surface"]
67
+ scores = compute_gap_scores(existing, tags, dead_themes=dead)
68
+ theme_names = [s[0] for s in scores]
69
+ assert "option_surface" not in theme_names
70
+
71
+ def test_pick_theme_returns_string(self):
72
+ theme = pick_theme(["momentum"], ["momentum"])
73
+ assert isinstance(theme, str)
74
+ assert len(theme) > 0