Skip to content

Commit e9076fe

Browse files
committed
Add annotated javascript of Polyfill pattern rewrite
1 parent d082571 commit e9076fe

File tree

1 file changed

+30
-0
lines changed

1 file changed

+30
-0
lines changed

chapters/metaprogramming/detecting-and-replacing-functions.md

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,3 +30,33 @@ However, we don't ever want to overwrite a prototype that we haven't created in
3030
What you need to do is only add the function if it doesn't already exist. That's where the existential assignment operator (`?=`) comes in. If we do `Array::filter ?= ...` instead, it will see if `Array::filter` already exists. If it does, then it will use the current version. If it doesn't, it will add yours.
3131

3232
Finally, because the existential assignment operator--when compiled--creates a few variables, we clean up the code by wrapping it in an [Immediately-Invoked Function Expression (IIFE)](http://benalman.com/news/2010/11/immediately-invoked-function-expression/). This hides those internal-use-only variables from leaking outside. So, if the function we're writing already exists, it runs, does basically nothing, and exits, affecting absolutely none of your code. But, if the function we're writing *doesn't* exist, we send out only the function we're writing as a closure, so only the function you've made affects the code. The internal workings of `?=` are hidden either way.
33+
34+
### Example
35+
36+
Below, we've compiled and annotated the coffeescript written in the solution above
37+
38+
{% highlight javascript %}
39+
// (function(){ ... })() is an IIFE, compiled in thanks to `do ->`
40+
(function() {
41+
42+
// This is from the `?=` operator, used to check if Array.prototype.filter (`Array::filter`) exists.
43+
// If it does, we set it to itself, and return. If it doesn't, then we set it to the function, and return the function.
44+
// The IIFE is only used to hide _base and _ref from the outside world.
45+
var _base, _ref;
46+
return (_ref = (_base = Array.prototype).filter) != null ? _ref : _base.filter = function(callback) {
47+
48+
// `element for element in this when callback element`
49+
var element, _i, _len, _results;
50+
_results = [];
51+
for (_i = 0, _len = this.length; _i < _len; _i++) {
52+
element = this[_i];
53+
if (callback(element)) {
54+
_results.push(element);
55+
}
56+
}
57+
return _results;
58+
59+
};
60+
// The end of the IIFE from `do ->`
61+
})();
62+
{% endhighlight %}

0 commit comments

Comments
 (0)