MAINT: One way to set sim_params and data_frequency.

There were sevaral places you could supply sim_params
in TradingAlgorithm (__init__, run). This got confusing
as its not clear who updated what and which one was the
correct one to use at each time.

Then there were to ways to define data_frequency, one in
__init__() and one in the sim_params which also added code
complexity.

This refactor makes it explicit that sim_params are to be
passed to __init__() only. Moreover, data_frequency is
only stored in sim_params. For backwards compatibility,
it can still be supplied separately but will link to
the one in sim_params.

For example, you could create new sim params via:

sim_params = create_simulation_parameters(data_frequency='minute')
algo = MyAlgo(sim_params)
algo.run(data)

In addition, perf_tracker only gets initialized in one place:
_create_generator() which should also make the various ways
of running an algorithm more deterministic.

This also fixes a bug with SimulationParameters where
you could not change the period_start. Unfortunately, the
current implementation still requieres an implicit call to
update the internal variables.
This commit is contained in:
Thomas Wiecki
2014-06-30 17:28:02 +02:00
parent 4c9cf1321d
commit 10885e1b77
9 changed files with 95 additions and 101 deletions
+17 -27
View File
@@ -93,8 +93,7 @@ class TestRecordAlgorithm(TestCase):
def test_record_incr(self):
algo = RecordAlgorithm(
sim_params=self.sim_params,
data_frequency='daily')
sim_params=self.sim_params)
output = algo.run(self.source)
np.testing.assert_array_equal(output['incr'].values,
@@ -161,8 +160,9 @@ class TestMiscellaneousAPI(TestCase):
algo.minute += 1
algo = TradingAlgorithm(initialize=initialize,
handle_data=handle_data)
algo.run(self.source, sim_params=self.sim_params)
handle_data=handle_data,
sim_params=self.sim_params)
algo.run(self.source)
class TestTransformAlgorithm(TestCase):
@@ -194,14 +194,6 @@ class TestTransformAlgorithm(TestCase):
self.assertEqual(len(algo.sources), 1)
assert isinstance(algo.sources[0], SpecificEquityTrades)
def test_multi_source_as_input_no_start_end(self):
algo = TestRegisterTransformAlgorithm(
sids=[133]
)
with self.assertRaises(AssertionError):
algo.run([self.source, self.df_source])
def test_invalid_order_parameters(self):
algo = InvalidOrderAlgorithm(
sids=[133],
@@ -261,26 +253,26 @@ class TestTransformAlgorithm(TestCase):
assert algo.registered_transforms['mavg']['class'] is MovingAverage
def test_data_frequency_setting(self):
self.sim_params.data_frequency = 'daily'
algo = TestRegisterTransformAlgorithm(
sim_params=self.sim_params,
data_frequency='daily'
)
self.assertEqual(algo.data_frequency, 'daily')
self.assertEqual(algo.sim_params.data_frequency, 'daily')
self.assertEqual(algo.annualizer, 250)
self.sim_params.data_frequency = 'minute'
algo = TestRegisterTransformAlgorithm(
sim_params=self.sim_params,
data_frequency='minute'
)
self.assertEqual(algo.data_frequency, 'minute')
self.assertEqual(algo.sim_params.data_frequency, 'minute')
self.assertEqual(algo.annualizer, 250 * 6 * 60)
self.sim_params.data_frequency = 'minute'
algo = TestRegisterTransformAlgorithm(
sim_params=self.sim_params,
data_frequency='minute',
annualizer=10
)
self.assertEqual(algo.data_frequency, 'minute')
self.assertEqual(algo.sim_params.data_frequency, 'minute')
self.assertEqual(algo.annualizer, 10)
def test_order_methods(self):
@@ -294,7 +286,6 @@ class TestTransformAlgorithm(TestCase):
for AlgoClass in AlgoClasses:
algo = AlgoClass(
sim_params=self.sim_params,
data_frequency='daily'
)
algo.run(self.df)
@@ -310,7 +301,6 @@ class TestTransformAlgorithm(TestCase):
for name in method_names_to_test:
algo = TestOrderStyleForwardingAlgorithm(
sim_params=self.sim_params,
data_frequency='daily',
instant_fill=False,
method_name=name
)
@@ -318,19 +308,18 @@ class TestTransformAlgorithm(TestCase):
def test_order_instant(self):
algo = TestOrderInstantAlgorithm(sim_params=self.sim_params,
data_frequency='daily',
instant_fill=True)
algo.run(self.df)
def test_minute_data(self):
source = RandomWalkSource(freq='minute',
start=pd.Timestamp('2000-1-1',
start=pd.Timestamp('2000-1-3',
tz='UTC'),
end=pd.Timestamp('2000-1-1',
end=pd.Timestamp('2000-1-4',
tz='UTC'))
self.sim_params.data_frequency = 'minute'
algo = TestOrderInstantAlgorithm(sim_params=self.sim_params,
data_frequency='minute',
instant_fill=True)
algo.run(source)
@@ -355,8 +344,7 @@ class TestPositions(TestCase):
factory.create_test_df_source(self.sim_params)
def test_empty_portfolio(self):
algo = EmptyPositionsAlgorithm(sim_params=self.sim_params,
data_frequency='daily')
algo = EmptyPositionsAlgorithm(sim_params=self.sim_params)
daily_stats = algo.run(self.df)
expected_position_count = [
@@ -634,7 +622,9 @@ def handle_data(context, data):
end = pd.Timestamp('1991-01-15', tz='UTC')
source = RandomWalkSource(start=start,
end=end)
algo = TradingAlgorithm(script=history_algo, data_frequency='minute')
sim_params = factory.create_simulation_parameters(
data_frequency='minute')
algo = TradingAlgorithm(script=history_algo, sim_params=sim_params)
output = algo.run(source)
self.assertIsNot(output, None)