5 ms·
Zero-Overhead Metaprogramming
- deleted 11y ago[deleted]
- Dewie3 11y ago> Metaprogramming and reflection are slow. That’s a common wisdom. [...], or really any metaprogramming abstraction in modern languages unfortunately comes at a price. Hold on. That might well be true for dynamic reflection. But metaprogramming is a wide term. It seems simple enough to give an example of metaprogramming that comes at no runtime cost: compile-time metaprogramming. Kiselyov has a catchy term for one approach to compile-time metaprogramming: "Abstraction without guilt". http://okmij.org/ftp/meta-programming/tutorial/ http://okmij.org/ftp/meta-programming/tutorial/
- bazzargh 11y agoThe paper discusses compile-time metaprogramming (and its disadvantages relative to this approach) in section 6. "Unfortunately, to enable the optimization of reflective operations, the MOP needs to be severely restricted and for instance metaobjects cannot change at runtime...Furthermore, most incarnations are not as powerful as MOPs in that they cannot redefine the language’s semantics."
- Dewie3 11y ago> The paper discusses compile-time metaprogramming (and its disadvantages relative to this approach) in section 6. Too bad that they didn't do it in the article, then. I guess it isn't "common wisdom" enough.
- smarr 11y agoThere is compile-time metaprogramming, staged programming, and many other things. Yes. Indeed the blog post neglects to go into detail about those for brevity. But, the point of the blog post was after all to get you guys to read the actual paper. Perhaps that wasn't explicit enough. Sorry. The main point of the paper is to show that runtime metaprogramming can be optimized with a classic JIT-compilation technique. After one sees it, it's kind of trivial, but it isn't done in common VMs.
- Dewie3 11y ago> But, the point of the blog post was after all to get you guys to read the actual paper. Don't be disingenuous in the process. I see you've changed the opening "Metaprogramming" to "Runtime metaprogramming", which is better IMO.
- cbsmith 11y ago> Furthermore, most incarnations are not as powerful as MOPs in that they cannot redefine the language’s semantics. Yeah, but there is a reason for that... It turns out to be less useful than you think, and altering language semantics in a meaningful way hampers the ability for an optimizer to make code execute efficiently (without the language's semantics, you really can't make assumptions). > MOP needs to be severely restricted and for instance metaobjects cannot change at runtime.. True as far as it goes, but to the extent that they can change, the performance penalty is there because you can't resolve issues at compile time. There are a variety of tricks employed to get you a hybrid model, where you effectively have a JIT optimize after dynamic binding, but if you truly have mutating metaobjects, there is an undeniable cost that you can't get around (and the benefits really aren't that huge).
- smarr 11y agoWith generalized polymorphic inline caches (dispatch chains) you get that cost down to the dynamic check and the JIT compiler can remove all reflective overhead. So, in the end, you get a powerful MOP without reflective overhead.
- cbsmith 11y ago> With generalized polymorphic inline caches (dispatch chains) you get that cost down to the dynamic check and the JIT compiler can remove all reflective overhead. ...which results in a scenario no different in terms of overhead or expressiveness, than you'd have with a static MOP with runtime dispatch.
- smarr 11y agoI don't follow that logic. First, I don't know what you mean with static. That you can't change the metaobject associated with a baselevel object? That's a loss of expressiveness. And, what do you mean with runtime dispatch? Static and runtime dispatch combined? I am not sure I really know what you got in mind. With dispatch chains, the runtime dispatch is resolved at runtime and the JIT compiler can inline through it. But, you need that runtime information. A static compiler, like for OpenC++ can't usually do that.
- PaulHoule 11y agoWe've been doing it a long time in Java. It is very practical for a program to write a Java class, compile it, then load the classfile, thus the metaprogrammed object runs as fast as anything in Java.
- cbsmith 11y agoAgreed... though it can be a bit of a pain to code that way.
- ksec 11y agoI care when i am going to see this in JRuby. And hopefully in MRI as well.
- smarr 11y agoIt is already used in the JRuby+Truffle backend. See for instance: http://www.chrisseaton.com/rubytruffle/pushing-pixels/ http://www.chrisseaton.com/rubytruffle/pushing-pixels/