Hacker News new | ask | show | jobs
by kazinator 1851 days ago
The original requirements should be addressed. The thing being matched is not just select, but actually any one of a set of symbols that appear in K.

We can stick that data into the pattern matching syntax using the or operator:

  3> (rewrite-case x '(foo bar * select * fox where * bravo)
       ((@(or select distinct partition from where
              group having order limit) * . @rest) ^(,(car x) _ . ,rest))
       (@else else))
  (foo bar * select _ fox where _ bravo)
Or put it into a variable:

  4> (defvarl K '(select distinct partition from where group having order limit))
  K
  5> (rewrite-case x '(foo bar * select * fox where * bravo)
       ((@(member @sym K) * . @rest) ^(,sym _ . ,rest))
       (@else else))
  (foo bar * select _ fox where _ bravo)
"If an object sym which is a member of K is followed by * and some remaining material, replace that by sym, underscore and that remaining material."

Hash table:

  6> (set K (hash-list '(select distinct partition from where group having order limit)))
  #H(() (select select) (where where) (limit limit) (order order)
     (having having) (distinct distinct) (partition partition) (group group)
     (from from))
  7> (rewrite-case x '(foo bar * select * fox where * bravo)
       ((@[K @sym] * . @rest) ^(,sym _ . ,rest))
       (@else else))
  (foo bar * select _ fox where _ bravo)
This code golfs moderately well: https://news.ycombinator.com/item?id=27227276