Hi Everyone
If you use the B and Q indicators in MetaStock you might be interested in
trying out the non-PREV versions given at the bottom of this
post.
Roy Larsen
www.metastocktips.co.nz
The
following Q Indicator has been sourced from the Equis website but with one small
adjustment (see point 2 below). This and the original B indicator provide the
model on which the revised indicators have been based. There are several points
about the basic Q indicator that are worthy of note, and these are listed and
commented on below.
{Q-indicator}
m:=Input("% Scalar trend
period",1,25,4);
n:=Input("% Scalar noise
period",1,500,250);
cf:=Input("% Scalar correction
factor",1,250,2);
p1:=Input("First moving average
periods",1,200,7);
p2:=Input("Second moving average
periods",1,200,15);
rev:=Mov(C,p1,E)-Mov(C,p2,E);
pds:=If(rev>0,1,-1);
dc:=ROC(C,1,$);
cpc:=If(pds<>Ref(pds,-1),0,(dc {*pds}
)+PREV);
trend:=If(pds<>Ref(pds,-1),0,(cpc*(1/m))+(PREV*(1-(1/m))));
dt:=cpc-trend;
noise:=cf*Sqrt(Mov(dt*dt,n,S));
trend/noise;
1.
The default "n" setting is 250
periods.
2.
The "cpc" variable has had the "*pds" expression commented
out.
3.
The "cpc" variable contains a PREV
function.
4.
The "trend" variable also contains a PREV
function.
There are several implications arising from these
points. The first is that this Q indicator will not plot any value with the
current default settings unless 265 or more data bars are loaded. This requires
more than 1 year of EOD data or 5 years of weekly data – a fact that makes it
less than useful with many securities.
For item 2 it can easily be shown that Q fails to plot
most negative values most when the price is trending down unless the "pds"
multiplier in the "cpc" variable is removed or commented out. The expression
"*pds" is redundant in the original B
indicator.
The PREV functions noted in items 3 and 4 can seriously
affect execution speed, particularly when exploring or testing large amounts of
historical data. The "cpc" variable is simply a counter that can be replaced by
code not requiring the PREV function. The "trend" variable is essentially a
re-settable exponential moving average that can be replaced by an EMA generated
within the Forum DLL.
A modifier for the "trend" variable has been added to
the non-PREV (NP) versions of B and Q, and the purpose of this is simply to
ensure an exact match between PREV and non-PREV versions when plotted on the
same data with the same user settings.
An "n" variable modifier has also been added, though
currently disabled, and its purpose is to reduce the "n" parameter in the
"noise" variable when otherwise insufficient data is loaded. This allows the
indicator to return a legitimate value, rather than N/A, for many securities
having less than the optimum amount of data. Results generated using less data
might be less accurate than desirable, but a valid plot is probably of more use
than an invalid one. I suggest that the default value for "n" be reduced to 100
for weekly data, whether or not the modifier is
enabled.
The Forum DLL exponential moving average permits an EMA
to be reset or reseeded at appropriate times, whereas the standard MetaStock
Mov() function does not allow such an
action.
Note that some versions of the B and Q indicators in
circulation use an exponential moving average in the "noise" variable, and
others use a simple moving average. Check this if you have difficulty matching
your B and Q values to results from the following
formulas.
{B Indicator NP} {Trend-Noise
Balance}
m:=Input("% Scalar trend
period",2,25,4);
n:=Input("% Scalar noise
period",2,500,250);
cf:=Input("% Scalar correction
factor",1,250,2);
p1:=Input("First moving average
periods",1,200,7);
p2:=Input("Second moving average
periods",1,200,15);
pds:=Mov(C,p1,E)>Mov(C,p2,E);
pds:=pds<>ValueWhen(2,1,pds);
dc:=ROC(C,1,$);
init:=Cum(pds>-1)=1;
cdc:=Cum(dc);
cpc:=cdc-ValueWhen(1,init+pds,cdc);
trend:=ExtFml("Forum.MOV",cpc,If(pds,1,2*m-1),E);
trend:=If(Sum(trend,2)=Sum(trend,2),trend,trend); {adds
an invalid bar}
dt:=cpc-trend;
{n:=LastValue(Min(Cum(1)-2*p2,n));} {adjusts "n" if not
enough bars are loaded}
noise:=cf*Sqrt(Mov(dt*dt,n,S));
noise:=If(Abs(trend)+Abs(noise)=0,1,Abs(trend)+Abs(noise));
100*Abs(trend)/noise;
{Q Indicator NP} {Trend
Quality}
m:=Input("% Scalar trend
period",2,25,4);
n:=Input("% Scalar noise
period",2,500,250);
cf:=Input("% Scalar correction
factor",1,250,2);
p1:=Input("First moving average
periods",1,200,7);
p2:=Input("Second moving average
periods",1,200,15);
pds:=Mov(C,p1,E)>Mov(C,p2,E);
pds:=pds<>ValueWhen(2,1,pds);
dc:=ROC(C,1,$);
init:=Cum(pds>-1)=1;
cdc:=Cum(dc);
cpc:=cdc-ValueWhen(1,init+pds,cdc);
trend:=ExtFml("Forum.MOV",cpc,If(pds,1,2*m-1),E);
trend:=If(Sum(trend,2)=Sum(trend,2),trend,trend); {adds
an invalid bar}
dt:=cpc-trend;
{n:=LastValue(Min(Cum(1)-2*p2,n));} {adjusts "n" if not
enough bars are loaded}
noise:=cf*Sqrt(Mov(dt*dt,n,S));
trend/noise;