~technomancy/fennel

Discussion of the Fennel programming language for contributors and users

https://fennel-lang.org

Re: Technique: using let for Rust-esque variable shadow chains

Details
Message ID
<87h8fvusq5.fsf@hagelb.org>
Download raw message
Benaiah Mischenko <benaiah@mischenko.com> writes:

> A similar pattern can be used in Fennel with let:
>
> ```fennel
> (let [x 1
>       x (+ x 2)
>       x (* x 2)
>       x (/ x 3)]
>   (print (.. "x: " x)))
> ```

This is a good general-purpose pattern, but you might find the arrow
macro more suitable in this case:

    (let [x (-> 1
               (+ 2)
               (* 2)
               (/ 3)]
      (print (.. "x: " x)))

As long as the previous value is always being fed into the next as the
first argument, it works nicely. But repeated-let is more general and
works in more cases.

> ```fennel
> (let [eff (moonshine 1024 768 moonshine.effects.crt)
>       _ (set eff.crt.feather 0.1)
>       _ (set eff.crt.distortionFactor [1.13 1.15])
>       eff (eff.chain moonshine.effects.vignette)
>       _ (set eff.vignette.radius 0.85)
>       _ (set eff.vignette.opacity 0.8)
>       eff (eff.chain moonshine.effects.fastgaussianblur)
>       eff (eff.chain moonshine.effects.filmgrain)
>       _ (set eff.filmgrain.size 2)
>       _ (set eff.filmgrain.opacity 0.5)]
>   eff)
> ```

I recently added the doto macro for side-effecty things like this where
the arrow won't work:

    (let [eff (doto (moonshine 1024 768 moonshine.effects.crt)
                (tset :crt :feather 0.1)
                (tset :crt :distortionFactor [1.13 1.15]))
          eff (doto (eff.chain moonshine.effects.vignette)
                (tset :vignette :radius 0.85)
                (tset :vignette :opacity 0.8))
          eff (eff.chain moonshine.effects.fastgaussianblur)
          eff (doto (eff.chain moonshine.effects.filmgrain)
                (tset :filmgrain :size 2)
                (tset :filmgrain :opacity 0.5))]
      eff)

It splices in the first value into successive forms as the first
argument, which is useful when you want to return the initial value with
some side-effects performed on it.

Looking forward to trying out your game.

-Phil