Skip to content

Instantly share code, notes, and snippets.

@SplittyDev
Last active August 23, 2017 02:23
Show Gist options
  • Save SplittyDev/9f0340593e8e92c7653d91b369acb78b to your computer and use it in GitHub Desktop.
Save SplittyDev/9f0340593e8e92c7653d91b369acb78b to your computer and use it in GitHub Desktop.
Iodine RFC: Match Expression

Iodine RFC: Match Expression

Proposed syntax (modified EBNF)

EBNF Syntax:

() = GROUP
[] = OPTIONAL
{}* = ZERO OR MORE
{}+ = ONE OR MORE

External rules: EXPR, STMT, BLOCK, IDENT, NUMBER, BOOLEAN_EXPR

MATCH               = "match" EXPR "{" MATCH_ARM { "," MATCH_ARM }* [ "," ] "}"
MATCH_ARM           = "case" MATCH_ARM_LEFT "=>" MATCH_ARM_RIGHT
MATCH_ARM_LEFT      = EXPR ({ "|" EXPR }+ | MATCH_ARM_LEFT_WHEN)
                    | NUMBER ( ".." | "..." ) NUMBER
                    | "var" IDENT MATCH_ARM_LEFT_WHEN
                    | "_"
MATCH_ARM_LEFT_WHEN = "when" BOOLEAN_EXPR
MATCH_ARM_RIGHT     = EXPR|STMT|BLOCK

Spec in human readable form

The match construct is an EXPRESSION.
Therefore, it MUST return a value (or null by default).

The match expression MUST contain at least one MATCH_ARM.

The match arms MUST be exhaustive.
Cases which are not covered MUST produce a compile-time exception.

All match arms MUST be followed by a COMMA (U+002C),
EXCEPT for the last match arm, where the COMMA is OPTIONAL.

Examples

// A valid match expression.
// Exhaustive through the use of an ANY ('_') match arm.
match some_number {
    case 0 => print ("Zero!"),
    case 2 | 3 | 5 | 7 | 11 => print ("A prime!"),
    case var x when x in [2, 3, 5, 7, 11] => print ("#{x} is a prime!"),
    case 13 ... 19 when animal => print ("A really old animal!"),
    case 13 ... 19 => print ("A teen!"),
    case var x when x > 1000 => print ("A big number!"),
    case _ => print ("Whoops"),
}

// A valid match expression on boolean values.
// Exhaustive by covering all possible values.
match some_boolean {
    true => print ("Yes!"),
    false => print ("No!"),
}

// Another valid match expression on boolean values.
// Exhaustive through the use of an ANY ('_') match arm.
match some_boolean {
    true => print ("Yes!"),
    _ => print ("No!"),
}

// An invalid match expression (non-exhaustive)
match some_number {
    case 0 => print ("Zero!"),
    case 1 => print ("One!),
} // This produces a compile-time error!
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment