6 ms·
treating them like functions with different semantics is a very good learning method If you mean run-time functions that act a bit funny about evaluation order
by kd0amg 8y ago
treating them like functions with different semantics is a very good learning method
If you mean run-time functions that act a bit funny about evaluation order, that mental model is incompatible with common introductory examples like `let`.
- reitzensteinm 8y agoNo, it's not. You eval the return value of the call. There is no loss of expressive power. Compile time macro expansion in this model is simply partial evaluation.
- kd0amg 8y agoIf `let` is a function, how and when are its arguments (say, `((x 2) (y 3))` and `(+ x y)`) evaluated?
- reitzensteinm 8y agoThe call would return: ((fn [x] ((fn [y] (+ x y)) 3)) 2) Which is in turn evaluated as you'd expect.
- kd0amg 8y agoHow and when are its arguments evaluated?
- reitzensteinm 8y agoThe first argument is not evaluated but used as data, the second argument is evaluated after the macro function returns, as part of the macro evaluation rules, i.e. (eval (let '((x 3) (y 5)) '(+ x y)))
- kd0amg 8y agoIn conclusion, it is definitely not working like a run-time function with different evaluation order.
- reitzensteinm 8y agoIn conclusion, it's working exactly as I laid it out in my original post: fn: (a b c) => (call a (eval b) (eval c)) mac: (a b c) => (eval (call a b c)) Everyone jumped on it, as production lisps don't implement macros this way. But it's the natural way to implement them in a SICP style metacircular evaluator, and a good way to learn them. This is about mental models, not implementation details. And in my opinion this thread is full of experts who have forgotten what it's like to not understand how macros work.
- kd0amg 8y agoThe sequence of events you describe is a thing that functions do not do at run time: they do not operate on pieces of syntax. Macro expansion time is a different series of events than run time. Macros operate on pieces of program syntax, not on anything from run time. Everyone jumped on it, as production lisps don't implement macros this way. … This is about mental models, not implementation details It looks to me like you're the one who brought up implementation details, talking about what happens "at a very low level." You're the one who has presented a questionable implementation strategy as a mental model and has been corrected on it multiple times by multiple people. Everyone else has been describing the semantics of macros. Having separate timelines for expansion and execution is a semantic distinction, not merely a common implementation strategy. And in my opinion this thread is full of experts who have forgotten what it's like to not understand how macros work. Your confusion is because you insist on a mental model of macros that is incompatible with their semantics. Letting that model go is necessary in order to understand macros. Otherwise, refusing to distinguish expansion time from run time, you are working towards reinventing fexprs.
- reitzensteinm 8y ago