Exercises in Programming Style–Kick Forward

NOTE : read the rest of the series, or check out the source code.

If you enjoy read­ing these exer­cises then please buy Crista’s book to sup­port her work.

exercises-prog-styles-cover

Fol­low­ing on from the last post, we will look at the Kick For­ward style today.

 

Style 8 – Kick Forward

You may also know this style as Con­tin­u­a­tion-Pass­ing Style, or CPS for short.

 

Constraints

  • All the con­straints from the Pipeline style
  • Each func­tion takes an addi­tion­al para­me­ter, usu­al­ly the last, which is anoth­er func­tion
  • That func­tion para­me­ter is applied at the end of the cur­rent func­tion
  • That func­tion para­me­ter is giv­en, as input, what would be the out­put of the cur­rent func­tion
  • The larg­er prob­lem is solved as a pipeline of func­tions, but where the next func­tion to be applied is giv­en as para­me­ter to the cur­rent func­tion

 

Now, the port for Crista’s solu­tion was pret­ty straight for­ward:

image

in the end, we end­ed up with a bunch of func­tions that:

  • takes in a con­tin­u­a­tion (the dot­ted lined box below)
  • exe­cutes the con­tin­u­a­tion whilst sup­ply­ing a con­tin­u­a­tion for the afore­men­tioned con­tin­u­a­tion

with the excep­tion of print­Text which expects a con­tin­u­a­tion that doesn’t expect a con­tin­u­a­tion.

image

Look­ing at these func­tions (or, build­ing blocks), I don’t real­ly see the exe­cu­tion flow just yet. Instead, I see rough­ly two exe­cu­tion paths start­ing with read­File and fil­ter­Chars.

Let’s rearrange things a lit­tle bit:

image

Ahhh, now things final­ly made sense when I fol­low the zigzag line!

image

Although CPS is an impor­tant pat­tern to under­stand and famil­iar­ize your­self with, I have nev­er writ­ten any non-triv­ial appli­ca­tion code in this style as it’s not straight for­ward and obvi­ous, and adds unnec­es­sary com­plex­i­ty in many cas­es.

Case in point:

image

 

That said, if you have ever used com­pu­ta­tion expres­sions in F# (async { }, seq { }, query { }, cloud { }, etc.) then you have writ­ten code in CPS with­out real­iz­ing.

Con­sid­er the sig­na­ture of bind:

image

Essen­tial­ly, com­pu­ta­tion expres­sions just takes your sequen­tial code and turns it into CPS code.

If you want to learn more about com­pu­ta­tion expres­sions, Scott Wlaschin has a great series of posts on the top­ic.

 

You can find all the source code for this exer­cise here.