# Zero clause in a \`match\` expression

**URL:** <https://racket.discourse.group/t/zero-clause-in-a-match-expression/1120>\
**Category:** Questions & Answers\
**Created:** [July 4, 2022, 9:23pm UTC](https://racket.discourse.group/t/zero-clause-in-a-match-expression/1120 "2022-07-04T21:23:54Z")\
**Posts on this page:** 7\
**Page:** 1

<div class="post-metadata">

**Author:** ![capfredf](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/capfredf/32/935_2.png) [@capfredf](https://racket.discourse.group/u/capfredf)\
**Post date:** [July 4, 2022, 9:23pm UTC](https://racket.discourse.group/t/zero-clause-in-a-match-expression/1120/1 "2022-07-04T21:23:54Z")

</div>

according to the [documentation](https://docs.racket-lang.org/reference/match.html#%28form._%28%28lib._racket%2Fmatch..rkt%29._match%29%29) for the `match` form,

we don't need to supply a clause to a match expression. For example:

```scheme
(define (g x)
  (match x))

```

However, this does not seem very useful to me, because calling `g` with any values will result in a runtime error.

I am wondering why match supports zero clause. Is it because `match` inherits the design from Andrew Wright's [original pattern matcher](https://3e8.org/pub/scheme/doc/match.pdf)?

---

<div class="post-metadata">

**Author:** ![samth](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/samth/32/3_2.png) [@samth](https://racket.discourse.group/u/samth)\
**Post date:** [July 5, 2022, 1:38am UTC](https://racket.discourse.group/t/zero-clause-in-a-match-expression/1120/2 "2022-07-05T01:38:30Z")

</div>

I'm pretty sure it's worked like this for a long time. Both `(case 1)` and `(cond)` are legal as well, so this is consistent.

---

<div class="post-metadata">

**Author:** ![capfredf](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/capfredf/32/935_2.png) [@capfredf](https://racket.discourse.group/u/capfredf)\
**Post date:** [July 5, 2022, 2:02am UTC](https://racket.discourse.group/t/zero-clause-in-a-match-expression/1120/3 "2022-07-05T02:02:29Z")

</div>

Yes, they are consistent in terms of syntax. But, `(cond)` are `(case 1)` are legal statically and dynamically, whereas `(match x)` is a runtime error.

---

<div class="post-metadata">

**Author:** ![joeld](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/joeld/32/38_2.png) [@joeld](https://racket.discourse.group/u/joeld)\
**Post date:** [July 5, 2022, 4:57pm UTC](https://racket.discourse.group/t/zero-clause-in-a-match-expression/1120/4 "2022-07-05T16:57:15Z")

</div>

I’m confused by the original post. The documentation says

> If no clause matches, then the `exn:misc:match?` exception is raised.

“Not supplying a clause” means no clause will match. So it would seem `match` does _not_ support a no-clause form, and the error is consistent with the docs.

Maybe you’re basing your original comment on the `...` in the `(match val-expr clause ...)` form at the top of the docs for `match`? Looks like that just needs to be corrected to `...+`.

---

<div class="post-metadata">

**Author:** ![benknoble](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/benknoble/32/16_2.png) [@benknoble](https://racket.discourse.group/u/benknoble)\
**Post date:** [July 5, 2022, 5:11pm UTC](https://racket.discourse.group/t/zero-clause-in-a-match-expression/1120/5 "2022-07-05T17:11:55Z")

</div>

@joeld, I believe the point is that while `(match x)` is syntactically  
valid (therefore "supported"), it is guaranteed to _always_ result in  
a runtime error.

The question is, as I understand it, why support this at all?

One argument put forth by @samth is that it is consistent with `case`  
and `cond`. @capfredf counters that they are not consistent  
semantically, however, since empty clauses of the latter two are  
silent (`(void? (case x))` and `(void? (cond))`), while the former is  
a runtime error.

Does that make sense?

---

<div class="post-metadata">

**Author:** ![joeld](https://yyz2.discourse-cdn.com/free1/user_avatar/racket.discourse.group/joeld/32/38_2.png) [@joeld](https://racket.discourse.group/u/joeld)\
**Post date:** [July 5, 2022, 5:33pm UTC](https://racket.discourse.group/t/zero-clause-in-a-match-expression/1120/6 "2022-07-05T17:33:29Z")

</div>

> I believe the point is that while `(match x)` is syntactically  
> valid (therefore "supported") …

If I provide a variable-arity function `foo` as follows

```scheme
(define (foo . n)
  (when (null? n) (error "Error!"))
  (format "Good: ~a" n))

```

Am I “supporting” the no-argument form, or “not supporting” it?

---

<div class="post-metadata">

**Author:** ![pcn](https://avatars.discourse-cdn.com/v4/letter/p/65b543/32.png) [@pcn](https://racket.discourse.group/u/pcn)\
**Post date:** [July 5, 2022, 5:41pm UTC](https://racket.discourse.group/t/zero-clause-in-a-match-expression/1120/7 "2022-07-05T17:41:29Z")

</div>

Let me try answering @capfredf why it's better to support a form like this.

1. It's more natural. Supporting the 0-clause case is as natural as supporting `(+)`, `(*)`, `(or)`, or `(and)`. Implementation-wise, it would take one extra step to restrict the inputs. `match`'s behavior, as @samth says, _is_ consistent with `(cond)` and `(case 1)`. It's just that `(cond)` and `(case 1)` default to `(void)`, while `match` defaults to error.

2. While it's not obvious why such a form is useful for a human writing programs, Racket code are also target for macro expansion. Allowing 0-clause `match` can simplify macros expanding to `match`, so each of them won't have to take care of the special case that could have naturally been taken care of by generalizing `match` to 0-clause.
