Combined rotation/ranking question
Author: techtrader007
Creation Date: 12/7/2010 9:12 AM
profile picture

techtrader007

#1
I would like to learn more about the ranking issues. Is there an example

1. sort Symbols in a watchlist for Indikator A in ListA : result for example in this List for symbol AAPL Rank decending = Position 5 of 100 symbols of the watchlist
2. sort Symbols again in the same watchlist for Indicator B in List B : result for example in this List for symbol AAPL Rank decending = Position 10 of 100 symbols of the watchlist
3. Sum these Ranking results in List3 Result:Position 5 (ListA) + Result:Position 10 (ListB) = Result 15
4. Sort all 100 symbols again in List3 again decending.
5. Condition Filter if Ranking Sum List 3 > Rank xYZ then ...

Are there any example around to play and learn with to improve my beginning program skills in c?
The two rotational scripts sofar I know, but it helps a litte bit. Any more advise would be fine.
Thanks.
profile picture

Cone

#2
I can't think of any ready-made examples for WLP6, but if you have a copy of "Combined Ranking Using ROA and P-E (Symbol Rotation)" from WLP4, that one comes pretty close.
profile picture

techtrader007

#3
Thanks Cone, but for me it important to get such examples or training examples if the forum wants to train people because getting more ideas helps people here and the forum get more active.
It doesn´t make sense to update to WL6 for me if this issues are not supported, because there are other things like automatic trading interfaces and so on, which are not working for WL Devolp. Unfortunally foreign people are not accepted as Fidelity customers to open an account to get this features.
profile picture

Cone

#4
That script was valid only for WLP because it required Fidelity fundamental data, but there's no problem supplying the script - we generally don't know if a forum pseudonym is a Fidelity customer or not, so it was basically a 50-50 chance that you already had it.

In fact, the script can be found in this topic.
profile picture

techtrader007

#5
thanks. Something to read. But before I have to cancel out all this fundamental stuff is there and easy shorter building block for a combined indicator ranking. And by the way is this not working in WL 6 only in WL4.
profile picture

Cone

#6
Of course that code won't work in WL6, but the methodology is the same. It all comes down to putting data into lists, sorting them, and then doing something with the result. Anyway, I'll take advantage of the topic and prepare some code for the March 2011 issue of AT Magazine's Trading Systems' Lab, and then you'll have it in black and white for WL6.
profile picture

Eugene

#7
techtrader007 asks:
QUOTE:
Cone said it will be in the February traders issue, but

My question concerning ranking is following:
I would like to rank for example an indicator1 sort this indicator in a watchlist and then you get Ranking Numbers so for example the highest value get 1 till the lowest value 100 if the watchlist contain 100 stock. Afterwards I would like to rank indicator2 and do the same. Afterwards I would like to sum up this scores for every symbol and rank again.
In Excel is this no problem, but I would work with these numbers and take for example a rotation for the 10 best symbols to buy and exit if the symbol falls out.
So to sum up different sorting.
Is this possible now .I know sofar the rotation script but only for one ranking.
Thanks for any advice.
profile picture

Eugene

#8
Some clarification needed.

1. Why not simply sum the two indicators up? Taking "RSI Rotation" for example:
CODE:
Please log in to see this code.

This way you get the combined score for two (three, N) indicators without the excessive sorting.

2. If for some reason you consider it's not applicable and independent sorting is required, then goes another question: what if sorting the lists end up with two very different symbol sets? For example:

* Sorting by lowest RSI spits out these 10 symbols: A, ADBE, AAPL...
* Sorting by highest TrendScore produces a different set: C, CSCO, CYAN...

What to do when symbols do not match? And if they do not match, we have to go back to Q.1 again: why not simply sum them up, ensuring that we will get 10 unique symbols?
profile picture

Eugene

#9
Later I thought about a different possible scenario: mixing the rankings to arrive at a new list.

The following demo strategy (built on top of RSI Rotation) ranks the symbols of a DataSet for lowest RSI, then for lowest ROC, selects Top N (3 by default) from each list, puts these candidates into a combined list, and uses that list for rotational trading. Hope that helps.
CODE:
Please log in to see this code.
profile picture

Eugene

#10
I noticed that this code doesn't handle duplicate symbols, should it happen:
CODE:
Please log in to see this code.

You might like to replace the above with the following code snippet:
CODE:
Please log in to see this code.
profile picture

techtrader007

#11
Thanks for your work.

Not real. I would like after sorting a list of an Indicator a positionscore like Excel function rank or old function Ind_List.IndexOf and a second run of Indicator2 list sort
get Postionscore and add them all in on Positionscore and sort again.

By the way I find if I test different data like yahoo or metastock format different script running times. Do you know which data is running more faster than others.
profile picture

Eugene

#12
QUOTE:
I would like after sorting a list of an Indicator a positionscore like Excel function rank or old function Ind_List.IndexOf and a second run of Indicator2 list sort
get Postionscore and add them all in on Positionscore and sort again.

It's not clear to me what you're after w.r.t. "Positionscore". What is that?
QUOTE:
By the way I find if I test different data like yahoo or metastock format different script running times. Do you know which data is running more faster than others.

Accessing Metastock data is known to be a little slower than accessing the locally stored data by such web download providers like Yahoo/MSN or ASCII with Cache feature enabled (and Cache built).
profile picture

Cone

#13
All data "runs" at the same speed, but data loading time can vary based on:

1. the provider options (for example Yahoo! back-adjusts on the fly)
2. data format (binary vs. text, and other overhead like MetaStock "Master" files)
3. data loading configuration. (for example, it's slightly faster for a provider to load 1000 Daily bars than the Most Recent 4 years of data)
4. and if on-demand is enabled.

Suggestions:
1. If you use ASCII, make sure to use the Cache option
2. For backtesting, update using the Data Manager first and turn off On-demand
3. For Y!, turn off the option to always return the partial bar, unless you're using it for live charting/trading

profile picture

techtrader007

#14
thanks Cone for the details.

Filter : acending/decending

Symbol/ Ind 1/ Rank/ Ind 2/ Rank2/ Rank1+Rank2
SYM C/ 1.9/ 1/ 50/ 2/ 3
SYM A/ 1.4/ 4/ 70/ 1/ 5
SYM E/ 1.7/ 3/ 40/ 3/ 6
SYM D/ 1.8/ 2/ 5/ 5/ 7
SYM B/ 1.3/ 5/ 30/ 4/ 9

here : acending Ind 1 then acending Ind 2 then acending Rank1+2

It looks in Excel like this. I would like to get the last Column
So for 3 worst in this case SYM B, SYM D, SYM E
profile picture

techtrader007

#15
thanks Eugene for your script and I hope you understand my defintion.
profile picture

Eugene

#16
I don't get the idea of summing two ranks up. Isn't my strategy doing about the same. "Rank" the first indicator, get the lowest/highest N symbols, repeat for indicator #2, get another ranking, mix them.

NOTE: As the topic's got "hijacked" with general questions later, the rest of the discussion (after post #16) does not have to do with the original "Combined Rotation" idea.
profile picture

trader rog

#17
Is it possible to rank the symbols of a DataSet by a custom formula? For example, instead of using RSI, rank based on % change from a moving average.

CODE:
Please log in to see this code.


Would this work with the RSI Rotation strategy?
profile picture

Eugene

#18
profile picture

trader rog

#19
Okay because I wasn't sure if my formula above is considered a "data series."

Also, I am trying to test a strategy that is similar to RSI Rotation but with intraday entries. The problem is, simulation using daily bars does not know the order of the intraday entries. So if there are 20 stocks that qualify for purchase but position management rules allow only 5, simulation ranks the list by low RSI for example, and will buy the top 5. This differs with live trading in that I will buy the first 5 that qualify by intraday time priority and ignore the rest. So, simulation uses RSI priority but real-time uses intraday time priority, and this can cause somewhat of a difference between the two results. Can intraday time priority be used within the rotation script? If not, can someone suggest a good way of tackling this issue?

On a side note, how can the number of symbols in the list be changed so that it has more symbols than that needed for actual positions?
I tried changing "number" to 500 to increase the size of the list. Is this correct?:
CODE:
Please log in to see this code.


Lastly, how can the symbols in the list be ranked randomly? I know simulated results would be different each time, but this can be useful to test for robustness. My solution was to comment out the statement below but all that changes is the order of the executed symbols, however, the trades are exactly the same.
CODE:
Please log in to see this code.


Any help is much appreciated.

profile picture

Eugene

#20
QUOTE:
Okay because I wasn't sure if my formula above is considered a "data series."

Yes it is even though you're making these calculations on the fly (in the Bars.Cache they will be stored as a DataSeries).
QUOTE:
On a side note, how can the number of symbols in the list be changed so that it has more symbols than that needed for actual positions?

Having 500 simultaneous positions in a rotation strategy doesn't make sense to me. Hope you understand what you're after better than I am.
QUOTE:
Lastly, how can the symbols in the list be ranked randomly?

Again, the meaning of it escapes me as you don't need a rotation strategy for random entries. Just set up a two-liner script with BuyAt* and SellAt* after some condition (e.g. fixed bars), use the Position Options PosSizer to limit the number of positions in the portfolio to N at a time ("Max open positions"), and off you go. Wealth-Lab's random Position.Priority will do the rest.
profile picture

trader rog

#21
I apologize for not being clear on what I'm trying to accomplish. I wasn't looking to have 500 simultaneous positions, I use the PosSizer to limit the number of positions. I'm looking to use my existing rotation code (since it is somewhat lengthy) to test the robustness of my strategy using random entries within a larger list from which to chose. I hope this makes more sense.
profile picture

Eugene

#22
The list from which to chose is your current DataSet. You can make it larger by adding more symbols to it.
profile picture

trader rog

#23
Right but I want to choose randomly from a subset of the DataSet. My DataSet has about 1,000 symbols and on any given day, there can be as many as 100 symbols that qualify according to the criteria in my script. However, I choose only 5 using the PosSizer. So, for example, I'm looking to select the 5 stocks randomly from the 100 symbol subset, not the 1,000 symbol DataSet.
profile picture

Cone

#24
I'm just coming in on the last couple posts, but if you know what the 100 symbol subset is, what problem do you have randomly picking 5 stocks from it? You could, for example, assign random priorities in the range 0 to 100, but -1 to 900 others.
profile picture

trader rog

#25
That's what I'm not sure how to do. I would like to assign random priorities to the subset, which itself varies everyday. Some days there will be 100+ symbols in the subset and other days there will be none. The main point of doing this is to try and match simulated and real-time results as closely as possible as described in my post above.
profile picture

Cone

#26
Okay, forget about priorities. How do you make your strategy aware of the "subset"?
profile picture

trader rog

#27
Exactly. A rotation script that randomly chooses stocks from the subset.
profile picture

Cone

#28
Seems you have 2 threads going on your intraday rotation system. Can we kill one of them?

QUOTE:
A rotation script that randomly chooses stocks from the subset.
Where's your code?
profile picture

trader rog

#29
Sure let's just continue our discussion in this thread.

To reiterate from the other thread, I would like to backtest using market orders to buy on a one tick break above the previous 5 minute bar high only if that price is x% below the previous day's close. I understand that I need to use series synchronization, I'm just not sure how to incorporate it into this script.

I would still also like to know how to randomly choose stocks from the subset using the code below.

Thanks for all your help.

CODE:
Please log in to see this code.
profile picture

Cone

#30
profile picture

trader rog

#31
I know this code doesn't work but is it at least close to working?

CODE:
Please log in to see this code.
profile picture

Eugene

#32
Not only GetProducts() isn't defined, you're not making any use of the products List in the code below.
profile picture

trader rog

#33
Should it be this instead?

CODE:
Please log in to see this code.
profile picture

Eugene

#34
Are you sure about shuffling a new (read: empty) List?
profile picture

trader rog

#35
Okay so it should just be list.Shuffle(); ?
I'm in the process of learning how to debug using visual studio express so hopefully it will make solving these issues easier going forward.

In the meantime, I'm also having trouble finding the right spot for the code below (which I pasted over from the website Cone referred me to in a post above).

CODE:
Please log in to see this code.
profile picture

Cone

#36
The position is okay. Here's how to implement it -

CODE:
Please log in to see this code.

profile picture

trader rog

#37
It works great. Thank you very much for working that out Cone!

At risk of taking up too much of your time, the other thing I would like to do is backtest using market orders to buy on a one tick break above the previous 5 minute bar high only if that price is x% below the previous day's close. More specifically, I'm having trouble synchronizing the previous day's close and then buying immediately after a 1 tick break above the previous 5 minute bar high. Thanks again Cone for helping me out.

CODE:
Please log in to see this code.



profile picture

Eugene

#38
I guess it's because you're synchronizing a new, empty DataSeries and subsequently assigning the close of the last 5-minute bar to it:
CODE:
Please log in to see this code.

Consequently, this code also operates on intraday scale (I guess you're interested in annual HV but it's intraday):
CODE:
Please log in to see this code.
profile picture

trader rog

#39
I got rid of the Prevclose DataSeries. What would be the best way to assign the previous day's close in the code below?

CODE:
Please log in to see this code.
profile picture

Cone

#40
In the Bars.Count loop with bar as the index, the first bar of the day in an intraday chart is:
CODE:
Please log in to see this code.


profile picture

Eugene

#41
profile picture

trader rog

#42
Okay I got it to compile, but no trades show up. I am using a 5 minute scale, 2 yr data range and 20% equity position size. Any idea what is wrong?

CODE:
Please log in to see this code.
profile picture

trader rog

#43
Any ideas on how to get the above script to work? I think it's a small oversight but I can't figure out what is wrong nonetheless.
profile picture

Cone

#44
What's the point about all the SetScaleDaily() and Synchronizing null DataSeries? You might as well remove all that and declare your DataSeries where they are actually used.

But the big problem, if you want to run this on intraday data is this:
if(Bars.IsIntraday) return;

Just read that statement out loud.
profile picture

trader rog

#45
Oops. I meant to have just if(Bars.IsIntraday) and not return. After deleting this line, however, I get an object reference error when trying to run the code.

On a side note, would it speed up the testing if I declared the DataSeries where they are used?

profile picture

Cone

#46
No, but if the idea is to be using synchronized Daily series, you're not doing that...

Look, you've even got a SetScaleDaily(); and then a SellAtClose(bar+1, p); You can't do that! Trading signals MUST occur in the base time frame.

I just don't get what you're trying to do. Maybe you should explain what the purpose of the Daily scaling is.
profile picture

trader rog

#47
I am trying to use daily screening criteria to generate signals and use intraday data for entries. Exits are at the closing price for the day.

These are the parameters I would like to use as the daily screening criteria:

CODE:
Please log in to see this code.


And I would like to exit at the day's close if either condition below is met. Would this work?

CODE:
Please log in to see this code.


profile picture

Cone

#48
If you're exiting at the close (actually it's not possible to do this if you're using closing data) and you're buying at Market, presumably on the open of the next day,...

1. What's the purpose of using intraday data at all?


2. This is an impossible (peeking) condition:
if ((High[bar+1] > High[bar]) && (High[bar] + 0.01 < Close[lastBarYesterday] *0.98))

In other words, how can you you buy at the open of bar + 1 already knowing what the High of bar + 1 is?
bar + 1, in general, is for trading signals only. If you use it anywhere else, you're probably peeking.

3. Is this series suppose to be based on intraday or daily data?
HV1 = HV.Series(Close, 100, 252);

Really the script is a mess. If you can express, precisely, the conditions required, I'll hammer this out for you. You must be precise and give me everything you need in one post. I (we) just don't have time to continually modify custom strategies.
profile picture

trader rog

#49
In a nutshell, I want all the code based on daily bars except for the entries, which should be based on 5 minute bars. So I need only one condition in the code based on 5 minute bars.

Preferred Method:
I would prefer to use an intraday market order to buy immediately following a one tick break above the previous 5 minute bar high only if that one tick above the high is 2% below the previous day's close. Ideally, the market order would be placed intrabar (not the next bar's open).

If preferred method above is not possible:
If an intrabar entry is not possible, then I would be okay with peeking for testing purposes only. In other words, if the current 5 minute bar breaks the high of the previous 5 minute bar, then use a buy limit order using the high of the previous bar plus one tick.

Here is a clean, simplified version of the code I would like to add these intraday entries to:

CODE:
Please log in to see this code.
profile picture

Cone

#50
QUOTE:
Ideally, the market order would be placed intrabar (not the next bar's open).
Strategies run when the interval completes. You can place market, stop, or limit orders at that time. So, your requirement is not compatible with a market order, but it is compatible with a stop order (which is a market order that is triggered when the stop price is attained).

There is no mention of a requirement for a rotation strategy. What is the purpose of adding all the complexity of a rotational strategy if there is no requirement for it?

profile picture

trader rog

#51
Good point. A stop order would be perfect.

You are right about not needing the rotational part since the strategy does not continuously hold n stocks.
profile picture

Cone

#52
I added a condition so that an entry wouldn't be triggered on the last bar of the day. Hopefully this is close enough for you because the requirements were not precise or well-defined. Note that you must install the Community.Components Addin Extension.

CODE:
Please log in to see this code.
profile picture

trader rog

#53
Thank you very much Cone! The code works great.

Before leaving this topic, I have one issue when running the strategy. If I test on as little as a year of data on 4,000 stocks, my RAM peaks out and the computer crashes. I have 6g of Ram, using the x64 version of Wealth-Lab, and using Bars.Cache.Clear at the end of the strategy. I tested the strategy using 15 minute bars and the same thing happens.

To run the strategy, I click on the Backtest on all Symbols in the DataSet tab. Am I doing something wrong here or is the DataSet just too big?
profile picture

Cone

#54
The DataSet is too big and/or the testing period is too great. For "as little as 1 year" of data for 4000 stocks with 5 minute bars, you're talking about 4000 x 78 bars/day * 251 days/year * 12 synchronized series (including OHLC/V and date) at 16 bytes per bar -> yields a "best case" memory requirement (no position created, etc.) of about 15G bytes. In practice it will certainly be more.
profile picture

HappyLoser

#55
This is an interesting thread.
What I am not sure about, though for system: RSIRotation :
Will the Execute() run for each symbol in the DataSetSymbols(the universe which I have setup) or will it only run once?

Regards
Faik
profile picture

Eugene

#56
In single symbol mode (correct) will run only once.
In MSB (incorrect), will run for each symbol.

More pointers in the Wiki FAQ | Strategies and WealthScript > Rotation strategies