Trouble with my strategy buying but not selling in pine editor - trading

I am using pine editor to make a strategy that buys when the D line which is the green line crosses under 17.5 and then sells when the D line crosses over 78. As you can see from the chart I have posted it should buy and sell a couple times but only buys once and does nothing else. I cant seem to figure out what I am missing. The bottom of the code is where I am telling it to by and sell in the strategy. Thanks
strategy("stochastic")
length = input(21, minval=1, title="length")
rsilength = input(21, minval=1, title="rsi length")
smoothk = input(4, minval=1, title="smoothk")
smoothd = input(10, minval=1, title="smoothd")
rsi = rsi(close, rsilength)
sto = stoch(close,highest(length),lowest(length), length)
K = sma(sto,smoothk)
D = sma(K,smoothd)
//plot(rsi, title="rsi", color=color.black)
plot(D, title="%D",color=color.green)
plot(K, title="%K",color=color.red)
hline(78,title="upper limit", color=color.red)
hline(17, title="lower limit",color=color.blue)
//plot(sto, title = "sto",color=color.black)
// === INPUT BACKTEST RANGE ===
FromMonth = input(defval = 8, title = "From Month", minval = 1, maxval = 12)
FromDay = input(defval = 5, title = "From Day", minval = 1, maxval = 31)
FromYear = input(defval = 2019, title = "From Year", minval = 2017)
ToMonth = input(defval = 9, title = "To Month", minval = 1, maxval = 12)
ToDay = input(defval = 1, title = "To Day", minval = 1, maxval = 31)
ToYear = input(defval = 9999, title = "To Year", minval = 2017)
// === FUNCTION EXAMPLE ===
start = timestamp(FromYear, FromMonth, FromDay, 00, 00) // backtest start window
finish = timestamp(ToYear, ToMonth, ToDay, 23, 59) // backtest finish window
window() => time >= start and time <= finish ? true : false // create function "within window of time"
// === EXECUTION ===
shares = 10000/close
buy = crossunder(D,17.5)
sell = crossover(D,78)
strategy.entry("buy", shares, when = window() and buy) // buy long when "within window of time" AND crossover
strategy.close("sell", when = window() and sell) // sell long when "within window of time" AND crossunder
This should buy and sell a couple times as seen highlighted in the picture.
https://ibb.co/37L0wSK That is the link, sorry I do not have enough rep to post images.

Your strategy.close() call wasn't using the same order id than the strategy.entry() call. I added markers in last 3 lines (you can turn them off via inputs) to show where your conditions are met.
Note: make sure you include the first line in the script when you
transport Pine scripts. It's the compiler directive that specifies
which version of Pine the code is using, so it's important.
//#version=4
strategy("stochastic")
length = input(21, minval=1, title="length")
rsilength = input(21, minval=1, title="rsi length")
smoothk = input(4, minval=1, title="smoothk")
smoothd = input(10, minval=1, title="smoothd")
showMarkers = input(true, "Show Markers")
rsi = rsi(close, rsilength)
sto = stoch(close,highest(length),lowest(length), length)
K = sma(sto,smoothk)
D = sma(K,smoothd)
//plot(rsi, title="rsi", color=color.black)
plot(D, title="%D",color=color.green)
plot(K, title="%K",color=color.red)
hline(78,title="upper limit", color=color.red)
hline(17, title="lower limit",color=color.blue)
//plot(sto, title = "sto",color=color.black)
// === INPUT BACKTEST RANGE ===
FromMonth = input(defval = 8, title = "From Month", minval = 1, maxval = 12)
FromDay = input(defval = 5, title = "From Day", minval = 1, maxval = 31)
FromYear = input(defval = 2019, title = "From Year", minval = 2017)
ToMonth = input(defval = 9, title = "To Month", minval = 1, maxval = 12)
ToDay = input(defval = 1, title = "To Day", minval = 1, maxval = 31)
ToYear = input(defval = 9999, title = "To Year", minval = 2017)
// === FUNCTION EXAMPLE ===
start = timestamp(FromYear, FromMonth, FromDay, 00, 00) // backtest start window
finish = timestamp(ToYear, ToMonth, ToDay, 23, 59) // backtest finish window
window() => time >= start and time <= finish ? true : false // create function "within window of time"
// === EXECUTION ===
shares = 10000/close
buy = crossunder(D,17.5)
sell = crossover(D,78)
strategy.entry("buy", shares, when = window() and buy) // buy long when "within window of time" AND crossover
strategy.close("buy", when = window() and sell) // sell long when "within window of time" AND crossunder
plotshape(showMarkers and buy, "buy", shape.triangleup, location.bottom, color.green, 0, text = "buy", size = size.tiny)
plotshape(showMarkers and sell, "sell", shape.triangledown, location.top, color.maroon, 0, text = "sell", size = size.tiny)
bgcolor(showMarkers ? window() ? color.green : color.maroon : na)

Related

How to assign one conditional label per stacked bar (not per stack) on time series ggplot in facet grid

I would love to have your input how to solve this issues.
I have a time series (x=date) ggplot with bars (y=cmass1), and my bars are on position="stack" using a factor (polymer) to display polymer types for each sample.
Each bar represents another sampling station (factor sample), and I would like to identify which bar is which station (factor "sample" in my data frame) and add the label above each bar.
I've come so far that I can show the "sample" labels, but then there appear multiple replicated labels (one for each data point in the stacked parts of the bar). But I need only one per bar!
Can someone help, how I can create one label per bar (above each bar) that identifies which sample it is (without manual annotation)?
Additional date display problem:
Also, on one date (11 November) I have two samples, and in this plot they are cumulated, but I would need them next to each - so two as stacked bars on one date (like with besides=TRUE, but that doesn't seem to work with stacked bars). Any help here?
I hope it is clear, and thanks so much for any help!
Cleo
The plot, where S1, S2 etc should be above each bar as a label
Dataframe view_partial
ggplot(Merg1[!(is.na(Merg1$campaign)),] ,
aes(date,y=cmass1,group_by(sample1), fill=polymer))+
geom_col(show.legend = T, alpha = 0.8, position="stack",
stat="identity")+
xlab("July 2021 November 2021 February 2022 July 2022") +
facet_grid(.~campaign, scales = "free_x",space = "free_x" )+
geom_point(aes(y=montsouris_mm*20 ),color="#A3009F",size=2.5, position="dodge")+
geom_point(aes(y=melun_mm*20 ),color="#558C8C",size=2.5, position="dodge")+
geom_point(aes(y=fauville_mm*20 ),color="#E8DB7D",size=2.5, position="dodge")+
scale_y_continuous(expand = c(0,0),limits=c(0, 1000), breaks = seq(0, 1000, by = 100),
sec.axis = sec_axis(~./20, name = "Precipitation (mm)",
breaks = seq(0, 50, by = 10))) +
scale_x_date(date_breaks = "1 day", labels = date_format("%d"))+
ylab(expression(bold(paste(~C[mass]~ (µg ~L^{-1}))))) +
theme(axis.text.x=element_text(color="black", size=12, angle=0, vjust=0.5),
axis.text.y=element_text(color="black", size=12, angle=0, vjust=0.5),
axis.ticks.x=element_blank(),
axis.title.x = element_text(size = 12,
color = "black",
face = "bold"),
strip.background = element_rect(color="white", fill="white", size=0.5,
linetype="solid"),
legend.text = element_text(color = "black",size = 12),
panel.grid.major = element_blank(),
panel.grid.minor = element_blank(),
panel.background = element_rect(size = 0.5,colour="#D4CDCB",
fill="white" ,linetype = 'solid'),
legend.key.height= unit(0.2, 'cm'),
legend.key.width= unit(0.4, 'cm'))+
scale_fill_manual(name = "", values = MPcol, breaks = c("abs","acrylic", "acrylic paints", "alkyd","epoxy", "pa", "pan_acrylic fibre", "pe", "polyester", "pp", "ps", "pu", "pvac", "pvc", "sbr", "vinyl copolymer"),
labels=c("Acrylonitrile butadiene styrene (ABS)","Acrylic", "Acrylic paint", "Alkyd", "Epoxy", "Polyamide (PA)", "Pan acrylic fibre", "Polyethylene (PE)", "Polyester (PET)", "Polypropylene (PP)", "Polystyrene (PS)", "Polyurethane (PU)", "Polyvinyl acetate (PVAC)", "Poly vinyl chloride (PVC)", "Styrene butadiene rubber (SBR)", "Vinyl copolymere"))+
theme(legend.position = "bottom",
legend.background = element_rect(fill = "#FFFCFB", # Background
colour = 1),
legend.title = element_text(family = "sans",
color = "black",
size = 10,
face = 2)) +
theme(panel.grid.minor = element_line(color = "#D4CDCB",
size = 0.15,
linetype = 2))+
theme(strip.text.x = element_text(size=14, face="bold",
vjust = 2, color="black")) +
#geom_text( label = label1, vjust = -1, position = position_dodge(0.90), size = 3, hjust=-0.5)+
labs(title = "Microplastics",
subtitle = "Mass Concentrations by Polymer Types",
caption = "Still missing S4 repeated samples and M1 in Campaign D. S4 in Campaign C cumulated repetaed samples. MPs >300µm are excluded, also natural particles are excluded.",
tag = "Fig. 5-1") +
theme(plot.title = element_text(family = "serif", # Font family
face = "bold", # Font face
color = 1, # Font color
size = 16, # Font size
hjust = 1, # Horizontal adjustment
vjust = 1, # Vertical adjustment
angle = 0, # Font angle
lineheight = 1, # Line spacing
margin = margin(5, 0, 0, 0)), # Margins (t, r, b, l)
plot.subtitle = element_text(family = "serif",
hjust = 1, size=14), # Subtitle customization
plot.caption = element_text(hjust = 0.25, size =11,
family = "serif",face = "italic"), # Caption customization
plot.tag = element_text(face = "italic"), # Tag customization
plot.title.position = "plot", # Title and subtitle position ("plot" or "panel")
plot.caption.position = "panel", # Caption position ("plot" or "panel")
plot.tag.position = "top") # Tag position

Set tickInterval in format HH:mm am/pm of a HIChart's Line chart using Swift 5.0

I want to set intervals as per the below image. I have tried to set using it below code.
let xAxis = HIXAxis()
xAxis.type = "datetime"
xAxis.dateTimeLabelFormats = HIDateTimeLabelFormats()
xAxis.dateTimeLabelFormats.day = HIDay()
xAxis.dateTimeLabelFormats.day.main = "%l:%M"
xAxis.min = NSNumber(value: ConverteddateFrom ) //Millisecond 12 AM midnight from starting of the day
xAxis.max = NSNumber(value: ConverteddateEnd) //Millisecond 12 AM to end of the day
xAxis.tickInterval = NSNumber(value: 4 * 3600 * 1000 )
xAxis.categories = DateList
options.xAxis = [xAxis]
let plotoptions = HIPlotOptions()
plotoptions.series = HISeries()
plotoptions.series.label = HILabel()
plotoptions.series.label.connectorAllowed = NSNumber(value: false)
// plotoptions.series.pointStart = 12
// plotoptions.series.pointInterval = NSNumber(value: 4)
// plotoptions.series.pointIntervalUnit = "AM"
options.plotOptions = plotoptions
let line1 = HILine()
line1.name = "Phase B"
line1.data = PhaseBList
let line2 = HILine()
line2.name = "Phase R"
line2.data = PhaseRList
let line3 = HILine()
line3.name = "Phase Y"
line3.data = PhaseYList
options.series = [line1, line2, line3]
options.responsive = responsive
options.colors = ["#7CB5EC","#F94F6C", "#FFB647"]
inputVoltage.options = options
but I didn't get proper x-axis with intervals. can anybody help me on this?
I am getting on x-axis points something like starting point as 20:00 to 16:00 with interval of 4 hours. I am expecting it from 12Am to 12Am. Also I can't see the data on graph.
You have 4 hour tick interval, so probably you need to change dateTimeLabelFormats from day to hour:
xAxis.dateTimeLabelFormats = HIDateTimeLabelFormats()
xAxis.dateTimeLabelFormats.hour = HIHour()
xAxis.dateTimeLabelFormats.hour.main = "%l %P"
xAxis.dateTimeLabelFormats.day = HIDay()
xAxis.dateTimeLabelFormats.day.main = "%l %P"
API Reference: https://api.highcharts.com/ios/highcharts/
I have got the solution -
1 - The problem was with the data presenting. Initially I was added the data array only whereas we have to add data along with its correspondence date. So it becomes array of array like this -
line1.data = [
[1562106600000, 0],
[1562121000000, 0.25]
]
2 - x axis time from 20:00 to 16:00 is because of UTC time. Solution is :
options.time = HITime()
options.time.useUTC = false
//options.time.timezone = "Asia/Kolkata" // If you want to set timezon you can
3 - converting the date into AM/PM in 12 hrs format.
xAxis.type = "datetime"
xAxis.dateTimeLabelFormats = HIDateTimeLabelFormats()
xAxis.dateTimeLabelFormats.hour = HIHour()
xAxis.dateTimeLabelFormats.hour.main = "%l %P"
xAxis.dateTimeLabelFormats.day = HIDay()
xAxis.dateTimeLabelFormats.day.main = "%l %P"
xAxis.min = NSNumber(value: ConverteddateFrom ) //Millisecond 12 AM midnight from starting of the day
xAxis.max = NSNumber(value: ConverteddateEnd) //Millisecond 12 AM midnight from ending of the day
xAxis.tickInterval = NSNumber(value: 4 * 3600 * 1000 )
options.xAxis = [xAxis]
This is how my graph is looking now -

Are there time zone abbreviations for UTC-12 and UTC+12?

I'm working on a problem where I want to do calculations on NSDates where a single NSDate gives different dd/mm/yyyy values in different time zones.
To do that I'm currently using New York City (EST) and Aukland, NZ, since they are frequently on different dates.
I'd like to be able to use the time zones on either side of the international date line, UTC+12, and UTC-12. There appears to be a standard abbreviation for UTC+12, ANAT, for Anadyr, Russia. However, the iOS implementation of TimeZone/NSTimeZone doesn't seem to recognize it. There also does not seem to be an abbreviation for UTC-12 (which would be in Alaska).
Does anybody know if there are such abbreviations for UTC+12 and UTC-12 that iOS (or Mac OS, for that matter) recognizes?
It looks like the answer is no.
I wrote some code to fetch all the system time zones, sort them by offset, and print them:
typealias timeZoneTuple = (abbreviation: String, name: String, offset: Int)
let timeZones = TimeZone.abbreviationDictionary
let mappedTimeZones: [timeZoneTuple] = timeZones
.map {key, value in
var offset = 0
if let timeZone = TimeZone(abbreviation: key) {
offset = timeZone.secondsFromGMT() / 3600
}
return (abbreviation: key, name: value, offset:offset)}
.sorted {$0.offset < $1.offset}
mappedTimeZones.forEach {
let abbreviation = $0.abbreviation.padding(toLength: 4, withPad: " ", startingAt: 0)
let name = $0.name.padding(toLength: 20, withPad: " ", startingAt: 0)
print("abbreviation = \(abbreviation), offset = \(name), val = \($0.offset)")}
The output of the above code is:
abbreviation = HST , offset = Pacific/Honolulu , val = -10
abbreviation = AKDT, offset = America/Juneau , val = -9
abbreviation = AKST, offset = America/Juneau , val = -9
abbreviation = PST , offset = America/Los_Angeles , val = -8
abbreviation = PDT , offset = America/Los_Angeles , val = -8
abbreviation = MDT , offset = America/Denver , val = -7
abbreviation = MST , offset = America/Denver , val = -7
abbreviation = CDT , offset = America/Chicago , val = -6
abbreviation = CST , offset = America/Chicago , val = -6
abbreviation = EDT , offset = America/New_York , val = -5
abbreviation = PET , offset = America/Lima , val = -5
abbreviation = EST , offset = America/New_York , val = -5
abbreviation = COT , offset = America/Bogota , val = -5
abbreviation = ADT , offset = America/Halifax , val = -4
abbreviation = AST , offset = America/Halifax , val = -4
abbreviation = CLT , offset = America/Santiago , val = -3
abbreviation = CLST, offset = America/Santiago , val = -3
abbreviation = ART , offset = America/Argentina/Bu, val = -3
abbreviation = BRST, offset = America/Sao_Paulo , val = -2
abbreviation = BRT , offset = America/Sao_Paulo , val = -2
abbreviation = GMT , offset = GMT , val = 0
abbreviation = WET , offset = Europe/Lisbon , val = 0
abbreviation = BST , offset = Europe/London , val = 0
abbreviation = WEST, offset = Europe/Lisbon , val = 0
abbreviation = UTC , offset = UTC , val = 0
abbreviation = CEST, offset = Europe/Paris , val = 1
abbreviation = WAT , offset = Africa/Lagos , val = 1
abbreviation = CET , offset = Europe/Paris , val = 1
abbreviation = CAT , offset = Africa/Harare , val = 2
abbreviation = MSD , offset = Europe/Moscow , val = 3
abbreviation = EAT , offset = Africa/Addis_Ababa , val = 3
abbreviation = IRST, offset = Asia/Tehran , val = 3
abbreviation = MSK , offset = Europe/Moscow , val = 3
abbreviation = EET , offset = Europe/Istanbul , val = 3
abbreviation = EEST, offset = Europe/Istanbul , val = 3
abbreviation = GST , offset = Asia/Dubai , val = 4
abbreviation = IST , offset = Asia/Calcutta , val = 5
abbreviation = PKT , offset = Asia/Karachi , val = 5
abbreviation = BDT , offset = Asia/Dhaka , val = 6
abbreviation = WIT , offset = Asia/Jakarta , val = 7
abbreviation = ICT , offset = Asia/Bangkok , val = 7
abbreviation = SGT , offset = Asia/Singapore , val = 8
abbreviation = HKT , offset = Asia/Hong_Kong , val = 8
abbreviation = PHT , offset = Asia/Manila , val = 8
abbreviation = KST , offset = Asia/Seoul , val = 9
abbreviation = JST , offset = Asia/Tokyo , val = 9
abbreviation = NZDT, offset = Pacific/Auckland , val = 13
abbreviation = NZST, offset = Pacific/Auckland , val = 13
So it looks like UTC-12, UTC-11, UTC-1, UTC+10, UTC+11, and UTC+12 are all missing from the "named" timezones that are available in Cocoa.
EDIT:
Based on a comment from #MattJohnson, it seems that the identifiers is a better way to get the list of available time zones. Modifying my code to use identifiers instead:
struct timeZoneStruct: CustomStringConvertible {
let identifier: String
var offset: Int
var description: String {
let displayOffset = String(format: "%3d", offset)
let displayIdentifier = (identifier + ",").padding(toLength: 30, withPad: " ", startingAt: 0)
return "identifier = \(displayIdentifier) offset = \(displayOffset)"
}
}
let timeZoneIDs = TimeZone.knownTimeZoneIdentifiers
let mappedTimeZones: [timeZoneStruct] = timeZoneIDs
.map {identifier in
var offset = 0
if let timeZone = TimeZone(identifier: identifier) {
offset = timeZone.secondsFromGMT() / 3600
}
return timeZoneStruct(identifier: identifier, offset: offset)}
.sorted {$0.offset < $1.offset}
mappedTimeZones.forEach {
print($0.description)
}
That yields a list of time zones ranging from UTC-11 (Pacific/Pago_pago) to UTC+14 (Pacific/Apia)
(There are quite a few duplicates for most time zones, so the list is too long to include here.)
So it seems there are defined time zones for offsets from UTC-11 to UTC+14. There is not a time zone for UTC-12 however, even though Baker Island, at Lat/Long: 0°12'N / 176°29'W, is in UTC-12. Curious.
This is the simplest way to get all timezones with their respective abbreviation.
P.S Not all timezones have their proper 3-Letter Abbreviations.
let timezoneList = NSTimeZone.knownTimeZoneNames
for i in 0...timezoneList.count - 1 {
let locale = NSTimeZone.init(name: timezoneList[i])
print("Region: \((locale?.name)!) Abbr: \((locale?.abbreviation)!)")
}
Also total 51, 3-lettered Abbreviations are present:
print(TimeZone.abbreviationDictionary.count)
You can also explore https://developer.apple.com/documentation/foundation/timezone for more.

Lua. Attempt to index global "a" (a nil value)

I'm getting the following error:
Attempt to index global "a" (a nil value)
local gfx = love.graphics
return{
new = function( Image, Animation, Time)
return{
current_frame = 1,
current_anim = 1,
image = Image,
a = Animation,
play = false,
time = Time or 0,2,
counter = 0,
update = function(dt)
if play then
counter = counter + dt
if counter >= time then
counter = 0
current_frame = current_frame + 1
end
if current_frame > #a[current_anim] then
current_frame = 1
end
else
end
end,
play = function()
play = true
end,
stop = function()
play = false
end,
set_animation = function(anim)
if anim > #a then error("there is no animation ", anim) return end
current_anim = anim
end,
draw = function(data)
gfx.draw(image, a[current_anim][current_frame], data[1], data[2])
end
}
end
}
it seems to me, that I do give "a" a value - a table, containing a set of images, which I assign through second parameter.
-----
local quad = love.graphics.newQuad
local anim_data = {
quad(0,0, 32, 48, 192, 256),
quad(32,0, 32, 48, 192, 256),
quad(64,0, 32, 48, 192, 256),
quad(96,0, 32, 48, 192, 256),
quad(129,0, 32, 48, 192, 256),
quad(162,0, 32, 48, 192, 256)
}
local image = love.graphics.newImage("images/player_animation.png")
image:setFilter("nearest","nearest")
Here I supposedly give 'a' a value
animation = require("animations"):new(
image,
{
{ -- idle
anim_data[1]
},
{ -- walk
anim_data[2],
anim_data[3],
anim_data[4],
anim_data[5],
anim_data[6]
},
},
0.2
)
animation.play()
The a you are looking for is part of the table you are returning from the new function. It is not visible from the scope of those functions.
The easiest solution is to move the values you've placed in the table up in the scope of the new function, encapsulating them. However, this removes them from the table, so they won't be visible outside of the new, .play, .pause, .draw, .update, or .set_animation functions.
A better solution is to employ a more typical OOP solution, so I would suggest reading chapter 16 of Programming in Lua: Object-oriented Programming. Once you've read that chapter, go read every other just to be safe (particularly 5, 6, and 11).
local gfx = love.graphics
return {
new = function (Image, Animation, Time)
local current_frame = 1
local current_anim = 1
local image = Image
local a = Animation
local play = false
local time = Time or 0,2
local counter = 0
return {
update = function (dt)
if play then
counter = counter + dt
if counter >= time then
counter = 0
current_frame = current_frame + 1
end
if current_frame > #a[current_anim] then
current_frame = 1
end
end
end,
play = function ()
play = true
end,
stop = function ()
play = false
end,
set_animation = function (anim)
if anim > #a then
error("there is no animation ", anim)
return
end
current_anim = anim
end,
draw = function (data)
gfx.draw(image, a[current_anim][current_frame], data[1], data[2])
end
}
end
}

F# - Flatten List/Range

I'm new to F# and am wondering how I would go about flattening a list.
Essentially in the database I store a record with a min_age and max_age range (this is a fictitious example for the sake of brevity - i am not agist!). My fields look something like the following:
id,
cost,
savings,
min_age,
max_age
I essentially have an F# class that acts as a one-to-one mapping with this table - i.e. all properties are mapped exactly to the database fields.
What I would like to do is flatten this range. So, instead of a list containing items like this:
saving_id = 1, cost = 100, savings = 20, min_age = 20, max_age = 26
saving_id = 2, cost = 110, savings = 10, min_age = 27, max_age = 31
I would like a list containing items like this:
saving_id = 1, cost = 100, savings = 20, age = 20
saving_id = 1, cost = 100, savings = 20, age = 21
etc.
saving_id = 2, cost = 110, savings = 10, age = 27
saving_id = 2, cost = 110, savings = 10, age = 28
etc.
Is there any in-built mechanism to flatten a list in this manner and/or does anyone know how to achieve this?
Thanks in advance,
JP
You might want to use Seq.collect. It concatenates sequences together, so in your case, you can map a function over your input that splits a single age range record to a sequence of age records and use Seq.collect to glue them together.
For example:
type myRecord =
{ saving_id: int;
cost: int;
savings: int;
min_age: int;
max_age: int }
type resultRecord =
{ saving_id: int;
cost: int;
savings: int;
age: int }
let records =
[ { saving_id = 1; cost = 100; savings = 20; min_age = 20; max_age = 26 }
{ saving_id = 2; cost = 110; savings = 10; min_age = 27; max_age = 31 } ]
let splitRecord (r:myRecord) =
seq { for ageCounter in r.min_age .. r.max_age ->
{ saving_id = r.saving_id;
cost = r.cost;
savings = r.savings;
age = ageCounter }
}
let ageRanges = records |> Seq.collect splitRecord
Edit: you can also use a sequence generator with yield!
let thisAlsoWorks =
seq { for r in records do yield! splitRecord r }
Agreeing with cfern's answer, but was wondering if this might benefit from seeing another "built-in" function used. Here's an alternative version of the splitRecord function that shows the library call for unfolding a sequence. No gain here other than having an example for Seq.unfold.
let splitRecord (r:myRecord) =
Seq.unfold (fun curr_age ->
if curr_age <= r.max_age then
Some({ saving_id = r.saving_id;
cost = r.cost;
savings = r.savings;
age = curr_age } ,
curr_age + 1)
else None)
r.min_age

Resources