0

Script

//@version=4
study(title="PlayGround", shorttitle="PG", overlay=true)

// My custom Median
median_custom(_src, _len) =>
    for _i = 1 to _len
        if _i == _len
            percentile_nearest_rank(_src, _i, 50)

// Built-in Median
median_builtin(_src, _len) =>
    percentile_nearest_rank(_src, _len, 50)

// 100 bars Median
median_len_100(_src) => percentile_nearest_rank(_src, 100, 50)
// 500 bars Median
median_len_500(_src) => percentile_nearest_rank(_src, 500, 50)

LEN1 = 100
LEN2 = 500

isBeforeDate = time < timestamp(2020,05,01,0,0,0)
len_custom = isBeforeDate ? LEN1 : LEN2

plot_space_delta = 10
plot(4*plot_space_delta + median_len_100(close),             "median_len_100", color = color.blue)
plot(3*plot_space_delta + median_len_500(close),             "median_len_500", color = color.white)
plot(2*plot_space_delta + median_builtin(close, LEN1),       "median_builtin", color = color.yellow)
plot(1*plot_space_delta + median_custom (close, len_custom), "median_custom",  color = isBeforeDate ? color.red : color.lime)

Output (ticker SPX)

Output_median_test

I was doing some testing around question Using percentile_nearest_rank with variable length to calculate running median

I thought I found a way to implement a running median with function median_custom(_src, _len),
by tricking the percentile_nearest_rank() into believing it's getting an integer parameter instead of a series.
By running median, I mean a median that accepts a changing length parameter as input.
By default that doesn't work, because the length parameter of percentile_nearest_rank() must be a fixed integer.

First I plot 3 reference medians:

  • Blue: median with fixed length of 100
  • White: median with fixed length of 500
  • Yellow: median with fixed length of LEN1 = 100

Then I plot my custom median (2 colors) with a color switch at the date cutoff on May 01, 2020 - Red: median with fixed length of LEN1 = 100 - Green: median with fixed length of LEN2 = 500

I expected the Red line to be of the same form as the Blue and Yellow lines.
Why? Because they all have a fixed median length of 100.
That is the case.

However, I also expected the Green line to be of the same form as the White line.
Why? Because they both have a fixed median length of 500.
This is clearly NOT the case.

Anybody that knows why the Green and White lines differ in shape, despite having the same fixed median length of 500?.

Bjorn Mistiaen
  • 6,459
  • 3
  • 18
  • 42

1 Answers1

0

You can't use percentile_nearest_rank(), nor any other built-in required to execute on every bar, in a for loop. That would require an embedded runtime for the loop, which isn't the case. So the loop version with the 100 length is working because the function is only returning the value of the loop's last iteration.

This will hopefully do what you need:

//@version=4
study(title="PlayGround", shorttitle="PG", overlay=true)

// 100 bars Median
median_len_100(_src) => percentile_nearest_rank(_src, 100, 50)
// 500 bars Median
median_len_500(_src) => percentile_nearest_rank(_src, 500, 50)

m100 = median_len_100(close)
m500 = median_len_500(close)
isBeforeDate = time < timestamp(2020,05,01,0,0,0)
m = isBeforeDate ? m100 : m500

plot(m100,  "median_len_100", color.blue, 8, transp = 60)
plot(m500,  "median_len_500", color.gray, 8, transp = 60)
plot(m,     "median_custom",  not isBeforeDate and isBeforeDate[1] ? na : isBeforeDate ? color.red : color.lime)

enter image description here

PineCoders-LucF
  • 8,288
  • 2
  • 12
  • 21