Welcome! Please see the About page for a little more info on how this works.

+1 vote
in core.match by

When matching on Class objects in core.match, the symbol normally used to name the Class object is treated by default as a pattern wildcard, just like any other symbol. The basic usage documentation shows this behavior and suggests local rebinding to get the intended behavior.

Rebinding is an adequate solution, but I find that, when writing or reading code, it is easy to overlook a missing binding. Another solution might be to use a fully-qualified class name:

(match [(type 1)]
  [java.lang.String] :string
  [java.lang.Long] :long
  :else :no-match)

By adopting this convention, developers wouldn't need to look at any scope larger than the pattern itself to know whether the class names will resolve correctly, making it easier to spot bugs when reading the code (and likely also making it easier to lint for this).

However, this syntax is not currently supported:

Syntax error (ClassFormatError) compiling fn* at (REPL:1:1).
Illegal field name "java.lang.String" in class user$eval1591

Symbols with no namespace which contain one or more periods are in the general case documented as indicating class names, and they do not work in local bindings (hence the error), so supporting this syntax shouldn't conflict with any other possible meanings of the symbol.

2 Answers

0 votes
0 votes

Keep in mind that class symbols evaluate to class instances, which are not constants and should not be in expanded code. So some special care would need to be taken here to expand to something that can be matched appropriately at runtime. I think that's probably possible, but this is maybe a bit trickier than it appears.