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

> ... complex numerator ... ... complex denominator ... /

Yes, this is why you are supposed to have short words. You should factor out the complex parts into short, self-contained, and descriptively named words, which is going to make your code much easier to read, test, and maintain.

For example:

Instead of:

  a b + c d + * e f + g h + * /
You should probably have:

  : compute-numerator   a b + c d + * ;
  : compute-denominator e f + g h + * ;
  : compute-ratio       compute-numerator compute-denominator / ;
Most (if not all) Forth books mention this as well.


Don't you now have actions in the middle of the computation that are putting names into a global dictionary? I'd at least give them names like tmp-numerator to put them into a namespace of local/temporary functions, and then "forget" them immediately after the computaton that references them.

What's the compiled version of : compute-numerator a b + c d + * ; look like? I imagine at the very least that there has to be a call to some run-time support routine to insert a compiled thunk under a name into the dictionary.


Yes, defining words like "compute-numerator" does add entries to the dictionary, but that happens entirely at compile time. Forth doesn't insert a "compiled thunk" at runtime, the word is compiled as a name bound to a sequence of code field addresses (CFAs). When invoked, it's just a jump through the usual inner interpreter. There's no runtime cost for defining the word itself. When you invoke "compute-numerator" at runtime, the inner interpreter simply threads through those CFAs. There's no indirection, JIT, or dynamic thunk creation involved. The only runtime effect is the word being executed when called. All linking is resolved at compile time.

If you're concerned about polluting the global dictionary, a common idiom is (which you already know):

  \ Define and forget immediately if temporary
  : tmp-numerator a b + c d + * ;
  tmp-numerator
  FORGET tmp-numerator
or alternatively, you can isolate temporary definitions in a separate vocabulary:

  VOCABULARY TMP-WORDS
  TMP-WORDS DEFINITIONS

  : numerator   1 2 + 3 4 + * ;
  : denominator 5 6 + 7 8 + * ;

  ONLY FORTH ALSO TMP-WORDS ALSO DEFINITIONS

  : compute-ratio numerator denominator / . ;

  compute-ratio

  ONLY FORTH DEFINITIONS
TL;DR: Defining intermediate words adds entries to the dictionary, but this happens at compile time, not runtime. There's no additional runtime overhead. Naming conventions, FORGET, or vocabularies can mitigate dictionary pollution / clutter, but still, factoring remains the standard idiom in Forth.

Note: In some native code compiling or JIT-based Forth implementations, definitions may generate machine code or runtime objects rather than simple CFA chains I mentioned, but even in these cases, compilation occurs before runtime execution, and no dynamic thunk insertion happens during word calls.

I hope I understood your comment correctly. Please let me know!




Consider applying for YC's Summer 2026 batch! Applications are open till May 4

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

Search: