If programming can be described as "making programs", metaprogramming could be described as "making programs making programs" - or something. You probably use metaprogramming every day perhaps without even noticing it.
Compared to other languages like Ruby or Python, JavaScript's metaprogramming features are not yet as advanced - especially when it comes to nifty tools like Operator Overloading, but ES6 is starting to level the playing field.
If I could up-vote recursively until the Inter-tubes segfaulted, I would on that link you provided.
A couple quotable lines from the article I have to throw out there are:
> One day, Netscape woke up from a truly epic bender to discover it had jammed a scripting language onto the web and millions of people were using it. Literally none of them liked it. Not one.
> Lots of programmers believe JavaScript is “basically” Scheme because it gives them something they want to believe: that the language they choose to use has some cachet and they don’t have to feel bad about it anymore.
Please, don't ever use foo/bar examples. No better way to bore and confuse the reader. It's the worst way to educate people about the possibilities of the thing you want to teach about.
In the past, I hardly ever used foo and bar in my examples, for that reason. Over the last two years or so, I've strived to start using them.
There's history of using foo/bar/baz in examples. So it's a very quick way to signal to the reader, "What this is isn't the important part. The meat of the discussion isn't in this; he crux of it lies elsewhere," and that's a pretty important thing.
There's a cost in using "real" examples. There's a cost to you the author in coming up with them, and then there's the cost to the reader who has to unpack the domain-specific concepts in the example you're synthesizing and disentangle it from what you're actually trying to demonstrate.
The global symbol registry sounds intriguing but dangerous. Does it now provide a mechanism for client side cross domain communication? The browser spends most of its time isolating different domains, but in this instance the feature seems to be explicitly added to allow for some kind of cross domain interaction. In turn however that would seem to bring with it all the security problems of allowing it - phishing sites can frame your web site and then farm all the information out of the global symbols. Which means any use of them would have to be very careful.
Does anybody have any insight on whether my interpretation here is correct?
Iirc, there are still ways to communicate between frames (postMessage rings a bell?) -- the global symbols don't really hold any information though, and are mostly just markers that are used in the code itself :)
Symbols are opaque aside from their tag. The global registry just means that you can have cross domain opaque identifiers which are equal; which is useful for communication.
If symbols of an object cannot be iterated over, does that mean they cannot be serialized into JSON? Also a symbol doesn't have a unique string representation, Symbol('foo') != another Symbol('foo'), does that mean they cannot be deserialized from JSON?
JSON is a very specific subset of JavaScript, and there is no literal syntax for Symbols, so there is no defined way to represent a symbol at the moment. Unless you wanted to encode them as a function call or something, which sounds terrible.
I don't think they can be represented in JSON. There are already other JS primitive types that can't be represented in JSON (Date) so at least it isn't introducing any inconsistency... JSON is only a subset of JS objects.
Not by default. But because there are possible overlaps in keys represented as strings it probably wouldnt be too helpful. Otherwise you could write your own .toJSON method to iterate over the symbol set if you really wanted to.
I don't know how the default JSON serializers/deserializers work, but I suspect that wouldn't work with symbols. You could probably get something working with Symbol.for().
I hadn't really been able see how useful well-known Symbols would be until I read this. My only thoughts now are that overriding binary operators in ES7 would be an amazing feature addition.
Why window.Symbol looks like a constructor, but works like a factory? Wouldn't it make more sense to have either a regular constructor (let symbol = new Symbol()) or a regular factory (let symbol = createSymbol())? If it looks like a duck, it should also walk like one.
When subclassing, what is the advantage of [Symbol.toStringTag] getter over the toString() method override? Is it just another way to do the same thing?
The Symbol workaround cannot ever clash with uses of `with`. Granted almost everybody considers `with` to be a bad idea nowadays, but that's part of the rationale.
> When you see code like rho == lho it could be converted into rho[Symbol.isAbstractEqual](lho), allowing classes to override what == means to them.
While there's not any technical error here (the examples follow proper alpha-conversion), the "l" and "r" in lho and rho stand for "left" and "right", respectively, so they should be switched.
In the Symbol.match example, "return [find];" should be... "return [index];"?
[+] [-] current_call|10 years ago|reply
Compared to other languages like Ruby or Python, JavaScript's metaprogramming features are not yet as advanced - especially when it comes to nifty tools like Operator Overloading, but ES6 is starting to level the playing field.
What isn't metaprogramming now?
This feels very relevant. http://journal.stuffwithstuff.com/2013/07/18/javascript-isnt...
[+] [-] AdieuToLogic|10 years ago|reply
A couple quotable lines from the article I have to throw out there are:
> One day, Netscape woke up from a truly epic bender to discover it had jammed a scripting language onto the web and millions of people were using it. Literally none of them liked it. Not one.
> Lots of programmers believe JavaScript is “basically” Scheme because it gives them something they want to believe: that the language they choose to use has some cachet and they don’t have to feel bad about it anymore.
[+] [-] thomasfoster96|10 years ago|reply
[+] [-] lispm|10 years ago|reply
The main difference: Lisp has simple printed representations for interned, uninterned and keyword symbols.
Lisp also has packages for namespaces of symbols.Here you can learn more about computing with symbols, in Lisp:
https://www.cs.cmu.edu/~dst/LispBook/
[+] [-] roopeshv|10 years ago|reply
In any case, I think the book parent is referring to: http://www.amazon.com/Common-LISP-Introduction-Computation-E...
[+] [-] kowdermeister|10 years ago|reply
[+] [-] carussell|10 years ago|reply
There's history of using foo/bar/baz in examples. So it's a very quick way to signal to the reader, "What this is isn't the important part. The meat of the discussion isn't in this; he crux of it lies elsewhere," and that's a pretty important thing.
There's a cost in using "real" examples. There's a cost to you the author in coming up with them, and then there's the cost to the reader who has to unpack the domain-specific concepts in the example you're synthesizing and disentangle it from what you're actually trying to demonstrate.
Do use foo and bar whenever possible.
[+] [-] kwhitefoot|10 years ago|reply
[+] [-] zmmmmm|10 years ago|reply
Does anybody have any insight on whether my interpretation here is correct?
[+] [-] girvo|10 years ago|reply
[+] [-] Manishearth|10 years ago|reply
[+] [-] braythwayt|10 years ago|reply
[+] [-] seanalltogether|10 years ago|reply
var foo = Symbol('foo')
over
var foo = Symbol()
[+] [-] kannanvijayan|10 years ago|reply
[+] [-] ww520|10 years ago|reply
[+] [-] loganfsmyth|10 years ago|reply
[+] [-] reverius42|10 years ago|reply
[+] [-] thinkingkong|10 years ago|reply
[+] [-] baddox|10 years ago|reply
[+] [-] thomasfoster96|10 years ago|reply
[+] [-] leishulang|10 years ago|reply
Edit: now it's back up online.
Any examples of using symbols for variants or flyweights ?
[+] [-] jarek-foksa|10 years ago|reply
When subclassing, what is the advantage of [Symbol.toStringTag] getter over the toString() method override? Is it just another way to do the same thing?
[+] [-] gchpaco|10 years ago|reply
[+] [-] zipolupu|10 years ago|reply
[+] [-] nawitus|10 years ago|reply
[+] [-] carussell|10 years ago|reply
See zipolupu's comment https://news.ycombinator.com/item?id=9790181
The article also says:
> When you see code like rho == lho it could be converted into rho[Symbol.isAbstractEqual](lho), allowing classes to override what == means to them.
While there's not any technical error here (the examples follow proper alpha-conversion), the "l" and "r" in lho and rho stand for "left" and "right", respectively, so they should be switched.
In the Symbol.match example, "return [find];" should be... "return [index];"?
[+] [-] mrottenkolber|10 years ago|reply
[deleted]
[+] [-] dang|10 years ago|reply
[+] [-] rcny1980|10 years ago|reply
[deleted]