Function within a function

I am struggling with how to map a list into a function.

Each item in the list, consists of a start date, end date, int and symbol.

q)requests:((2021.06.07;2021.06.09;53696;Sent);(2021.06.12;2021.06.14;81840;Sent))

I then have a function that creates all dates in between the start date and end date, then fills a table:

q)fillDates:{[a;b;c;d] f:a + til (b - a) + 1;(Date:date$(f);CrewID:int$(c);Status:`symbol$(d))}

q)fillDates[2021.06.07;2021.06.09;53696;`Sent]

Date       CrewID Status


2021.06.07 53696  Sent  

2021.06.08 53696  Sent  

2021.06.09 53696  Sent

Where I am having difficulty is trying to process all items in the requests list, something like:

fillDates each requests

Such that the  result would look like this:

Date       CrewID Status


2021.06.07 53696  Sent  

2021.06.08 53696  Sent  

2021.06.09 53696  Sent

2021.06.12 81840  Sent  

2021.06.13 81840  Sent  

2021.06.14 81840  Sent

When I try:

q)fillDates[requests]

{[a;b;c;d] f:a + til (b - a) + 1;(Date:date$(f);CrewID:int$(c);Status:symbol$(d))}[((2021.06.07;2021.06.09;53696;Sent);(2021.06.12;2021.06.14;81840;`Sent))]

q)type fillDates[requests]

104h

I get a projection of the function and I am not sure how to proceed. 

I would be grateful if somebody could point out a better way than my tortured approach.

Many thanks

Dean

You want . (index/apply) https://code.kx.com/q/ref/apply/ <o:p>
</o:p>

and /: (each-right) https://code.kx.com/q/ref/maps/ <o:p>
</o:p>

and raze https://code.kx.com/q/ref/raze/ <o:p>
</o:p>

<o:p> </o:p>

Combining these three to end up with:<o:p></o:p>

q)requests:((2021.06.07;2021.06.09;53696;Sent);(2021.06.12;2021.06.14;81840;Sent))<o:p></o:p>

q)fillDates:{[a;b;c;d] f:a + til (b - a) + 1;(Date:date$(f);CrewID:int$(c);Status:`symbol$(d))}<o:p></o:p>

q)raze fillDates ./: requests<o:p></o:p>

Date       CrewID Status<o:p></o:p>

------------------------<o:p></o:p>

2021.06.07 53696  Sent<o:p></o:p>

2021.06.08 53696  Sent<o:p></o:p>

2021.06.09 53696  Sent<o:p></o:p>

2021.06.12 81840  Sent<o:p></o:p>

2021.06.13 81840  Sent<o:p></o:p>

2021.06.14 81840  Sent<o:p></o:p>

q)<o:p></o:p>

<o:p> </o:p>

From: personal-kdbplus@googlegroups.com [mailto:personal-kdbplus@googlegroups.com] On Behalf Of Dean Williams
Sent: Monday, March 15, 2021 12:33 PM
To: Kdb+ Personal Developers <personal-kdbplus@googlegroups.com>
Subject: [personal kdb+] Function within a function<o:p></o:p>

<o:p> </o:p>

CAUTION: External email. Do not click links or open attachments unless you recognize the sender and know the content is safe.<o:p></o:p>

I am struggling with how to map a list into a function. <o:p>
</o:p>

<o:p> </o:p>

Each item in the list, consists of a start date, end date, int and symbol. <o:p></o:p>

q)requests:((2021.06.07;2021.06.09;53696;Sent);(2021.06.12;2021.06.14;81840;Sent))<o:p></o:p>

I then have a function that creates all dates in between the start date and end date, then fills a table:<o:p></o:p>

q)fillDates:{[a;b;c;d] f:a + til (b - a) + 1;(Date:date$(f);CrewID:int$(c);Status:`symbol$(d))}<o:p></o:p>

q)fillDates[2021.06.07;2021.06.09;53696;`Sent]<o:p></o:p>

Date       CrewID Status<o:p></o:p>

------------------------<o:p></o:p>

2021.06.07 53696  Sent  <o:p></o:p>

2021.06.08 53696  Sent  <o:p></o:p>

2021.06.09 53696  Sent<o:p></o:p>

Where I am having difficulty is trying to process all items in the requests list, something like:<o:p></o:p>

fillDates each requests<o:p></o:p>

Such that the  result would look like this:<o:p></o:p>

Date       CrewID Status<o:p></o:p>

------------------------<o:p></o:p>

2021.06.07 53696  Sent  <o:p></o:p>

2021.06.08 53696  Sent  <o:p></o:p>

2021.06.09 53696  Sent<o:p></o:p>

2021.06.12 81840  Sent  <o:p></o:p>

2021.06.13 81840  Sent  <o:p></o:p>

2021.06.14 81840  Sent<o:p></o:p>

When I try:<o:p></o:p>

q)fillDates[requests]<o:p></o:p>

{[a;b;c;d] f:a + til (b - a) + 1;(Date:date$(f);CrewID:int$(c);Status:symbol$(d))}[((2021.06.07;2021.06.09;53696;Sent);(2021.06.12;2021.06.14;81840;`Sent))]<o:p></o:p>

q)type fillDates[requests]<o:p></o:p>

104h<o:p></o:p>

I get a projection of the function and I am not sure how to proceed. <o:p></o:p>

I would be grateful if somebody could point out a better way than my tortured approach.<o:p></o:p>

Many thanks<o:p></o:p>

Dean<o:p></o:p>


Submitted via Google Groups

Many, many thanks David.

Thank you Brian

You can vectorize parts of the function and have it perform faster (half the time) as well:

requests:1000000#((2021.06.07;2021.06.09;53696;Sent);(2021.06.12;2021.06.14;81840;Sent))

\t a:raze fillDates ./: requests

2346

fillDates2:{[a;b;c;d]dt:a+til each 1+b-a;cnt:count each dt;data:raze each(dt;cnt#'c;cnt#'d);(Date:data 0;CrewID:`int$data 1;Status:data 2)}

\t b:fillDates2 . flip requests

1215

a~b

1b

Alvi
 
That was very a interesting solution. Thank you.