Hacker Newsnew | past | comments | ask | show | jobs | submitlogin

> it's more like pattern matching and replacing patterns with expressions

Scheme macros use pattern-matching.

> loop Body is { Body; loop Body }

This, though, is definitely strange. I’m not quite sure how it works.



It's just a case of a pattern definition including references to itself, which are then linked to its definition before use. In the same way function definitions often contain reference themselves, which are linked to complete the definition.

   uint64_t alignBitsLeft(uint64_t x) {
      return ((x >> 63) == 1)) ? x : alignBitsLeft(x << 1);
   }
The pattern "alignBitLeft(uint64_t)" definition starts in line 1, but is not completed until line 3. Yet line 2 references that pattern, before the definition is complete.

This works, because of a linking step at definition completion, where the "alignBitsLeft" reference gets linked to the now complete "alignBitsLeft" definition.

Similarly for:

> loop Body is { Body; loop Body }

The "loop Body" definition beings, including a reference to itself. Once the whole definition has been built up, the "loop Body" reference gets linked back to the "loop Body" definition. Ready for use.

--

Another way to look at this is memoization (at compile or run time). When you evaluate the second line of this:

  n is 1;
  loop { print n; n is n + 1; }
You get this:

  { print n; n is n + 1; loop { print n; n is n + 1; }}
If we cache that definition before evaluating it, when we get to the embedded loop clause, we don't need to compute it again. We have already computed that exact loop pattern before and can reuse the result (over and over).


You can do exactly that, and this is how this is defined in the built-in library

https://github.com/c3d/xl/blob/fast/src/builtins.xl#L222

How it works is what I tried to document in the document above. The trick is to have some fixed semantics on how rewrites are done, but a lot of freedom in how this is implemented. And this is far from perfect ATM.

For example, if you write "X is 2", this can be implemented as a constant, as a function returning a constant, or as a macro. However, if you write "X is seconds" in Tao3D, where "seconds" returns the current number of seconds in the clock, then it can no longer be a constant value. You still can use macro replacement (or inlining) or turn it into a function.

More details here: https://xlr.sourceforge.io/#compiling-xl




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: