Activated Strategies
Author: snout_hound
Creation Date: 4/9/2009 12:17 PM
profile picture

snout_hound

#1
Do activated strategies need to be written in different ways from those that are used in back testing? For instance, the strategy that I am currently working on looks generically something like the following pseudocode.

CODE:
Please log in to see this code.


The first part that initializes the strategy involves computing various DataSeries for different indicators such as moving averages, channel lines, etc for the time interval of the back test. But when a strategy is being run in real time, I'm not sure of the WL5 control flow and how things work. For instance, does the loop over bars make sense for a strategy that is being actively run? Does the strategy initialization get done every time I advance to a new bar? Is there a difference between activating a strategy for real time intraday data versus one that operates on a daily trading time frame?
profile picture

Eugene

#2
QUOTE:
Do activated strategies need to be written in different ways from those that are used in back testing?

Generally no, if they make no use of AtClose orders but be sure to check for considerations summed up in the WLP User Guide, Strategy Monitor > Employment Notes.
QUOTE:
For instance, does the loop over bars make sense for a strategy that is being actively run?

Yes.
QUOTE:
Does the strategy initialization get done every time I advance to a new bar?

Yes. The whole Execute method body is, well, executed once every bar.
profile picture

snout_hound

#3
QUOTE:
Yes. The whole Execute method body is, well, executed once every bar.


I guess I am confused then since it would seem that I have something like the following for an activated strategy.

foreach bar
{
Execute()
}

If I then inline the Execute method gives something like the following:

foreach bar
{
// Initialize the strategy.
init_strategy();

// Loop over tf1 bars and simulate trades.
for( int bar = some_start_bar; bar < Bars.Count; bar++ )
{
// Evaluate entry and exit criteria and respond appropriately.
}
}

So then for each new bar, I am looping over all the bars in some time frame. And it would appear that I am then also recomputing the initialization step when, in principle, all I need to do is incrementally update the various DataSeries that were computed in the first initialization. This all seems very computationally inefficient. Am I missing something?

Is there any documentation on what the code flow looks like that calls the Execute() method for both back testing and activated strategies? Something like pseudocode or a flow chart would be useful.
profile picture

Cone

#4
QUOTE:
The whole Execute method body is, well, executed once every bar.
I'm pretty sure Eugene meant to say "...well, executed once for each symbol".

The Execute() method is the "entry point" for your script, a program. It's called after the data for the current symbol, the "context or primary symbol" is loaded. It's your job to do something inside the Execute method. The data for the primary symbol is available to your script by referencing the Bars object. Generally, you'll create indicators and then run through each bar in Bars once to execute your strategy. Alerts will occur if the strategy has a trading signal based on the data from the last bar of the data loaded. That's all there is to it.

QUOTE:
This all seems very computationally inefficient.
But it's not inefficient on memory. Most strategies run in milliseconds and then the garbage collector can clean up anything in memory that's no longer needed. CPUs are usually well under-utilized (low duty cycle), so there's usually plenty of CPU available, but not so much for memory. There are other considerations, like complexity and ease of use, that you'll have to consider when you start designing and programming your more-efficient successor TA app to Wealth-Lab. ;)
profile picture

snout_hound

#5
Thanks. You did not mention if there was any documentation that provided a high level overview of the computational cycle that runs when using WL for either back testing or as an activated strategy. Does such info exist in either a document or the Wiki?

BTW, I was not trying to be disparaging about the efficiency of WL. Properly used, it may be very close to optimal. I am just trying to increase my level of understanding so that I don't write a stupid strategy in terms of computational efficiency. Hence the desire to understand better what is going on "under the hood" when my strategy is being executed.
profile picture

Eugene

#6
QUOTE:
I'm pretty sure Eugene meant to say "...well, executed once for each symbol".

What I had on my mind is: "...executed once every new bar appears", because the topic starter wondered whether his initialization is performed every time it advances to a new bar - that is true in real time.
profile picture

snout_hound

#7
Thanks for the clarification. I assume this means, as you said previously, that the Execute() method is run every time you advance to a new bar. I would also assume that the class object which the Execute() method is a part of continues to exist from bar to bar rather than being reconstructed. Is that true? If so, are there standard ways to incrementally update indicators such as moving averages? It seems that something like this would be important if running a strategy in real time on 1 minute bars, especially if multiple symbols were involved. I'm thinking that the current way that I have things coded would result in things like exponential moving averages being completely recalculated from scratch every time the Execute() method is called.

Also, it seems like the way things are currently coded, I would have a for loop over all the data bars in the data set when I really only want to execute that code for the current bar that I have just advanced to. Does this seem correct or am I missing something? I probably need to go back and review that section of the users guide.

Perhaps I also need to review some of the other sample strategies that come with WL or are on the Wiki. Is there a particular strategy that you would recommend that I study as a model of an efficient strategy when running on a 1 minute time frame?
profile picture

Cone

#8
QUOTE:
the Execute() method is run every time you advance to a new bar.
Let's be specific: The Execute() method is entered whenever the chart data is loaded into memory and when a new bar is added to the Bars object in a streaming chart.

When is chart data loaded?
1. When you click "Go"
2. When you strike "F5"
3. When you click the "Run Strategy" button in the Editor.
4. When you start Streaming
5. When you initialize a Workspace that has Charts

QUOTE:
I would also assume that the class object which the Execute() method is a part of continues to exist from bar to bar rather than being reconstructed.
Look at the Strategy code. Execute() is an overridden method of your Strategy class derived from WealthScript.

QUOTE:
incrementally update indicators
Unless you're saving an indicator to a cache or disk, no such thing exists. The script must be completely re-run every time Execute() is entered, so "things like exponential moving averages being completely recalculated" is entirely correct.

QUOTE:
Does this seem correct or am I missing something?
I've explained this at least twice already, so I don't know why you're hung up on it.