Arc Forumnew | comments | leaders | submitlogin
First-class lexical&global environments?
5 points by binx 5909 days ago | 8 comments
They have at least two important applications.

1. Defining new local variables without the let expression which introduces an extra pair of "(" and ")". It also helps us define new non-local variables in any nested scope.

2. I believe that first-class macros plus first-class global environments can be used to separate namespaces. Arc doesn't need an official module system, but it's not bad to let the user build their own.

There might be more applications of them. If continuations can be first-class, why shouldn't environments?

Efficiency may be a reason. But according to my knowledge, in Arc culture, expressiveness and power are never compromised for efficiency.



5 points by ryantmulligan 5909 days ago | link

I disagree with 2. An official module system will be much more effective at using libraries once they are created. Without some module system, there won't be a way to create a standard directory for external dependencies to be found through a standard module system. If someone did make a system and it was adopted by a lot of people, I believe that it should be made standard so as to prevent splinter module systems.

-----

1 point by binx 5909 days ago | link

A proper module system which works well with non-hygienic macros seems to be difficult to make. I don't know whether it would be better if macros are made first-class.

-----

4 points by almkglor 5909 days ago | link

I disagree. Recall that macros in Arc have precedence in expressions over non-macros; that is, if obj in (obj x) is globally a macro, even if it is used as a variable name, all (obj x) will be replaced by the macroexpansion. Note that this applies for all x.

Suppose we have nested macro expressions. The inner macro will not see the expression until the outer macro processes that value; the outer macro might even decide to completely bollix the inner macroexpression.

   (macro ....
     (sub-macro ...))
Now suppose we declare a "using" macro, which replaces all symbols inside its expressions for other symbols, i.e.

  arc> (using
      (
         foo   bar
         nitz  koo)
      '(foo bar nitz koo))
  (bar bar koo koo)
Obviously, if we postulate another macro 'foo, the replacement done by using will prevent the macro 'foo from transforming any part of the (using ...) form.

The benefit of this using macro is as a basis for module systems. Suppose we have a module system such that:

  arc> (macex
    '(module foo
        (def foo () 0)
        (mac bar () nil)))
  (do
     (= (*members* 'foo) (list 'foo 'bar))
     (def foo--foo () 0)
     (mac bar--foo () nil))
  arc> (module foo
        (def foo () 0)
        (mac bar () nil)))
  <#procedure:foo--bar 3 mac>
  arc> (macex '(w/module foo (bar)))
  (do (foo--bar))
(Damn. I've been reading too many EWD's, my language is starting to sound academic.)

-----

1 point by binx 5909 days ago | link

Rewriting all symbols is what the CL package system does. Of course, the CL package system does not really rewrite symbols after parsing, it chooses different symbols for the same string in different packages when parsing.

A true module system just rewrites all identifiers that are globally referenced, without touching local identifiers and quoted symbols.

-----

1 point by almkglor 5909 days ago | link

Why not local identifiers? It won't hurt anyway, since:

  (fn (x) x) == (fn (y) y)
Quoted symbols are more problematic. The problem is that you can't determine how macros will bash quoted symbols. For example, (tag (x) ...) implicitly creates 'x. And prior to replacement, you can't be sure if the 'tag here is pg:arc1's tag or some other module's 'tag macro.

An alternative is to make the (pr ...) versions of similarly-named symbols in different modules the same; this probably involves hacking (coerce ... 'string) to cut out the module name for symbols.

-----

1 point by binx 5909 days ago | link

If a module doesn't export any macros, the problem would go away. Just macroexpand all function definitions, then all quoted symbols can be detected.

Hygienic macros can also be dealt properly, mzscheme is an example. But I have no idea how Arc macros can work well with modules.

Maybe the CL package system is the only way.

-----

1 point by almkglor 5908 days ago | link

Hmm, probably means we need a separate macro namespace. Heck, stuff like (let obj (table) (obj 1)) doesn't do as you expect, because of the mixing of macros in the same namespace as functions and values.

-----

3 points by bramsundar 5909 days ago | link

Aren't macros already first-class?

-----