Arc Forumnew | comments | leaders | submitlogin
Eliminating consif/conswhen and only, and beyond
3 points by akkartik 4931 days ago | 9 comments
At the top of arc.arc:

  ; don't like names of conswhen and consif
I've been writing them a different way in wart:

  (consif a b) => (maybe cons a :to b)

  (conswhen f a b) => (maybe cons (check a f) :to b)
Here's maybe:

  def maybe(f a b/to)
    if a
      (f a b)
      b
(Uses param aliases: http://arclanguage.org/item?id=15254)

While I'm at it, I'm also unhappy with the name only. Ah, maybe can replace it in the common case of unary functions (17 out of 20 uses in arc 3.1).

  (only f a) => (maybe f a)
This works because wart is flexible about how many arguments a function can take. Extra args are silently dropped, and missing args are nil by default. maybe exploits both scenarios.

And for non-unary functions? I'd replace:

  (only f a b c)
with

  (and a (f a b c))
Especially since it's already a common pattern in the arc codebase. (See app.arc)

---

consif makes a call to cons if its first arg is not nil. conswhen generalizes the nil check to be parameterizable. I want to make this generalization elsewhere as well. iflet binds and executes body if the binding is not nil, but I sometimes am stuck generalizing it:

  (let x (...)
    (when (f x)
       ..))
I'm not sure what to do about this case for now. Maybe something like:

  (let var val :provided check . body)
But that seems like a control abstraction (http://arclanguage.org/item?id=13664).


1 point by Pauan 4931 days ago | link

"I've been writing them a different way in wart"

My first impression is: too verbose. But it's quite easy to define consif and conswhen in terms of maybe, so I think that is best:

  (def consif (a b)
    (maybe cons a b))

  (def conswhen (a b)
    (maybe cons (check a f) b))
This is similar to defining ++ and -- in terms of zap. In fact, `maybe` has a similar look and feel to `zap`, except that it's functional.

---

How about letmaybe?

  (letmaybe x f ...
    ...)

  ->

  (let x ...
    (when (f x)
      ...))

-----

1 point by akkartik 4931 days ago | link

The point is that consif isn't a good name. It isn't obvious what the condition is, and it isn't obvious that it returns b if the condition isn't met. conswhen is even more egregious since its connection to consif is totally different from if vs when.

-----

1 point by Pauan 4931 days ago | link

Sure, and it's great that we can generalize the behavior into `maybe`, but if the problem is the bad names then we should come up with better names.

-----

1 point by akkartik 4931 days ago | link

Yeah, I couldn't think of anything better than maybe, and I'd love to find something better.

-----

3 points by rocketnia 4929 days ago | link

The name of 'pushnew isn't bad at all, so how about the names "construe" for 'consif and "conscheck" for 'conswhen? They would be cousins to the hypothetical 'pushtrue, 'pushcheck, and 'consnew.

The name of 'maybe could be... um... "combinetrue".

-----

3 points by rocketnia 4929 days ago | link

As far as "let :provided" goes, I'm thinking "checklet":

  (let x init
    (when (f x)
      ...body...))
  ==>
  (checklet x f init
    ...body...)
Implementation:

  (def fn-checklet (test x body)
    (test&body x))
  (mac checklet (var test x . body)
    `(fn-checklet ,test ,x (fn (,var) ,@body)))

-----

3 points by rocketnia 4929 days ago | link

"how about the names "construe" for 'consif"

Whoops, "construe" is an English word. XD Better call it "cons-true".

-----

2 points by Pauan 4929 days ago | link

Or for more confusion we can call it "const" as in "cons-t" :P

-----

1 point by akkartik 4929 days ago | link

Oops, typo: (only f ...) should be (only.f ...).

-----