The Fold function in thinkScript can be used to iterate over a list of data points and perform a calculation on each point.
Contents
show
thinkScript Fold Syntax
def <result> = fold <index> = <start> to <end> [ with <variable> [ = <init> ] ] [ while <condition> ] do <expression>;
The index
variable operates as a loop counter.
thinkScript Fold Function Explained
Several knowledgeable developers in the thinkScript community have written about the Fold function.
If you’re interested in learning more, check out the links below.
thinkScript Fold Function Examples
The following examples and snippets are helpful for anyone who wish to experiment with the thinkScript fold function.
All credit goes to its respective owners.
Visual Aid for Fold Index Length
# Visual Aid for Fold Index Length
# Nube
# v.01 9.18.18
# Sum of bar numbers using Sum() and Fold
input barsAgo = 5;
def bn = BarNumber();
# Subscript for n bars from current
script barsAgo {
input n = 0;
def bn = BarNumber();
def c = close;
def barsBack = if !IsNaN(c[-n]) && IsNaN(c[-(n+1)])
then bn else barsBack[1];
plot barsAgo = barsBack;
}
def checkFold = fold i = 0 to barsAgo with b do b + GetValue(bn,i);
def checkSum = Sum(bn,barsAgo);
AddChartBubble(bn == barsAgo(barsAgo), HL2, "Bar \n" +barsAgo(barsAgo),Color.Gray,0);
AddChartBubble(bn == barsAgo(0), HL2, "Bar "+barsAgo(0),Color.Gray,0);
AddChartBubble(bn == barsAgo(0), low, "Sum() of "+barsAgo+" Bars = "+checkSum+"\nNote: This Bar is 1 in a Sum()",Color.Light_Gray,0);
AddChartBubble(bn == barsAgo(barsAgo-1), low, "Sum Last \nBar "+bn,Color.Light_Gray,0);
AddChartBubble(bn == barsAgo(0), high, "Fold of "+barsAgo+" Bars = "+checkFold+"\nNote: This Bar is Index 0 in a Fold" ,Color.White);
AddChartBubble(bn == barsAgo(barsAgo-1), high, "Fold Last\nBar "+bn ,Color.White);
AddChartBubble(bn == barsAgo(barsAgo), high, "Including this bar is \nwhy you see the +1\nin the Fold index" ,Color.White);
# f/ Visual Aid for Fold Index Length
Fold Debugging
# KillingHours
def n = 20;
plot learn =
fold i = 0 to n #<-- how far to loop
#with s #<-- loop variable. (used within the looping | Can be removed if not needed)
#while cond #<-- while this condition is true. (can be removed if not needed)
do i; #<-- execute this code (comment out loop var)
#do s + i; #<-- execute this code (uncomment loop var)
learn.SetPaintingStrategy(PaintingStrategy.VALUES_BELOW);
Mobius’ Fold Example/Clarification
# Fold Example/Clarification
# Mobius
# 1.23.2017
# UpTheCreek: In the following snippet, I was expecting that the
# intermediate values of p could be used in the evaluation of the
# while loop. It didn't seem work as expected. Does the intermediate
# variable not get exposed as it updates?
#
# def Data = fold i = 0 to active
# with p
# while active and p < 70000
# do data[1] + volume;
# Mobius: You can only use one value to store in "p". In the
# following example, Data is holding the cumulative value while
# p is testing for active
declare lower;
def active = if SecondsFromTime(0930) > 0 and
SecondsTillTime(1600) >= 0
then 1
else 0;
def Data = fold i = 0 to active
with p
while active
do if data[1] < 70000
then data[1] + volume
else double.nan;
plot CumVol = data;
CumVol.SetPaintingStrategy(PaintingStrategy.Histogram);
addChartBubble(active[-1] == 0 and active == 1, data, data);
Linus’ Fold Example
# Fold Example
# Linus
# 10.12.2015
# On a 1 year daily, with the multiplier set to 1.0, you should get 252 bars.
# A multiplier of 0.5 would give you 126 bars
input referenceLength = 252;
input c = close;
input multiplier = 1.0;
input showLabel = Yes;
def n = Floor(HighestAll(if !isNaN(c)
then barNumber()
else Double.NaN) * multiplier);
def SumC = fold i = 0 to n
with v
do v + getValue(c, i);
plot Avg = SumC / n;
plot RefAvg = Average(c, referenceLength);
RefAvg.SetDefaultColor(Color.YELLOW);
AddLabel(showLabel, "Total Bars = " + barNumber() + " Dynamic length = " + n, Color.GRAY);
Happy testing!
Hello, I’d like to be clarified the mechanics for using in the function FOLD an index parameter with negative value that represents to read forward values within the array, not backwards.
Mainly with the parameter GetValue. The use case is for the known study of fractal formation. I’m confuse where would be the exact positioning of the bar array/vector when start to apply negative sequence [-i] and the positioning with the subsequent counting with incremental of the negative index [-i+n]. Which bar of the array and towards what direction of the array start counting the negative index by any new iteration within the FOLD loop? As an example, this is the code I’m using:
def maxSideLength = Fractal_Signal_Period + 50;
def upRightSide = fold i1 = 1 to maxSideLength + 1 with count1 while count1 != Fractal_Signal_Period and count1 != -1 do
if GetValue(high, -i1) > high or (GetValue(high, -i1) == high and count1 == 0) then -1
else if GetValue(high, -i1) high or (GetValue(high, i2) == high and count2 >= 1) then -1
else if GetValue(high, i2) < high then count2 + 1 else count2;
Many thanks for your support.