       value ?= "#{exp}[#{label}]"
       recurse: (for elem, i in elems
         [elem, "#{value}[#{i}]"])
+  (pattern) ->
+    elems = inside pattern
+    hasSplat = no
+    requiredElems = 0
+    for elem in elems
+      if isSplat elem
+        hasSplat = yes
+      else
+        requiredElems++
+    trigger: isList pattern
+    cache: true
+    cond: (exp) -> ["$sequenceSize(#{exp}) #{if hasSplat then '>=' else '=='} #{requiredElems}"]
+    assignTo: (exp) ->
+      recurse: (for elem, i in elems
+        if isSplat elem
+          [elem, "$sequenceSplat(#{i}, #{elems.length - i - 1}, #{exp})"]
+        else
+          [elem, "$sequenceAt(#{i}, #{exp})"])
   (pattern) ->
     [constr, elems...] = inside pattern
     label = "'#{constr.token}'"

  [constr, args...] = elems
  items = args.map(compileImpl).join ', '
  "({\"#{constr.token}\": [#{items}]})"

compileList = (elems) ->
  # "[#{elems.join ', '}]"

patternMatchingRules = [
  (pattern) ->
    trigger: pattern.label is 'numerical'
    cond: (exp) -> ["#{exp}" + " == #{pattern.token}"]
  (pattern) ->
    trigger: pattern.label is 'const'
    cond: (exp) -> ["'#{pattern.token}' in #{exp}"]
  (pattern) ->
    trigger: pattern.label is 'name'
    assignTo: (exp) ->
