A Reintroduction to JavaScript
developer.mozilla.org
developer.mozilla.org
1. Douglas Crockford videos: http://www.yuiblog.com/crockford/
2. Eloquent JavaScript intermediate level tutorials: http://eloquentjavascript.net/contents.html
for (var key = 0, value; value = someArray[key++];) {
// value is already defined by for loop
console.log('index: ' + key, 'value: ' + value);
}
Also, I finally understand closures:"Whenever JavaScript executes a function, a 'scope' object is created to hold the local variables created within that function. It is initialised with any variables passed in as function parameters. This is similar to the global object that all global variables and functions live in, but with a couple of important differences: firstly, a brand new scope object is created every time a function starts executing, and secondly, unlike the global object (which in browsers is accessible as window) these scope objects cannot be directly accessed from your JavaScript code... A closure is the combination of a function and the scope object in which it was created."
In fact, this was an even better way to write that loop in 2006:
for( var value, i = -1; value = array[++i]; ) {
console.log( 'index: ' + i, 'value: ' + value );
}
Basically the same thing except for the pre-increment instead of postincrement. In some of the browsers of that day (at least IE), preincrement was faster. And this version gives you the correct array index inside the loop, unlike the off-by-one in the other version.I was so proud of myself when I discovered this alternative that I wrote a recipe for the jQuery Cookbook recommending it as the fastest way to iterate over a typical array of objects such as you might receive from a JSON request.
It also used to be a great idea to optimize your machine code programs by looking up the CPU cycles for each instruction. Fewer cycles = faster code.
Of course, that doesn't work any more, what with pipelining and out-of-order execution.
Alas, these nifty JavaScript loops are not the fastest any more either. Fewer operations != faster code.
The optimization guy for V8 explained this to me at Google I/O 2012. He said that V8 can optimize the heck out of references into an array where all the types are the same (either primitive values, or objects that all have the same properties). But if you ever try to reference outside the bounds of the array, it throws the whole thing back into deoptimized code.
And that is the problem. These nifty loops rely on reading the nonexistent element just past the end of the array. That's their termination condition.
It turns out that with modern optimizing compilers, the plain old traditional JavaScript loop is faster across the board:
for( var i = 0, n = array.length; i < n; ++i ) {
var value = array[i];
console.log( 'index: ' + i, 'value: ' + value );
}
(There is still a minor benefit to using preincrement instead of the more traditional postincrement in some modern browsers.)I put together a JSPerf for this a while ago:
http://jsperf.com/mikes-loops/2
I was quite embarrassed to learn how poorly my clever loop works in modern browsers!
What's really embarrassing is IE js performance.
Since I keep an ancient copy of of Netscape 9.0.0.6 on my computer I decided to try it so see how much browsers have improved. It doesn't seem to upload results I'll post them here in the same order as the testing page.
17.25 16.72 5.94 8.81 18.90 23.28 20.92 23.58
This is on the same computer that was pulling 5000+ on the fastest tests. Browsers have come a long way.
It is frequently and recently updated.
https://developer.mozilla.org/en-US/docs/Web/JavaScript/A_re...
Perhaps you should add your bit?
Given that the loop also fails to complete if someArray contains a falsy value, I'd say this trick falls into the "too cute to be safe" category.
Note that this trick should only be used
for arrays which you know do not contain
"falsy" values (arrays of objects or DOM
nodes for example). If you are iterating
over numeric data that might include a 0
or string data that might include the
empty string you should use the i, len
idiom instead.1. Crockford's C style with cached array length (fast and flexible, but verbose):
for (let index = 0, length = array.length; index < length; index += 1) {
console.log(index, array[index]);
}
2. Functional style (terse and flexible, but slow): array.forEach((value, index) => console.log(index, value));
3. Python style (fast and terse, but not flexible): for (let value of array) {
console.log(value);
}
By "flexible" I mean being able to e.g. iterate over items with odd indexes or in reverse direction.One question though, it says:
If you want to append an item to an array, the safest way to do it is like this:
a[a.length] = item; // same as a.push(item);
a.push() variant seems more elegant to me. Why is a[] variant "safer"?https://developer.mozilla.org/en-US/docs/Web/JavaScript/Refe...
So, why should a[a.length] be safer?
1. https://developer.mozilla.org/en-US/docs/Web/JavaScript/A_re...
Maybe remove the "2006" from the headline (again).
Edit: Just noticed inglor say it was a caching issue and the page was updated today.
> typeof null
"object"
Contrast that with: > typeof undefined
"undefined"
Go figure :)If you check the language specification you can see that `null` is in fact not an object - it's something called a 'primitive value type', just like numbers, strings, undefined and booleans.
Here http://es5.github.io/#x8 :)
> There's our first brush with JavaScript objects! Did I mention that strings are objects too? They have methods as well
Also, how do NaN and infinity fit in? I'm guessing they're special cases of Number types?
"hello"
Not an object. new String("hello")
Object.Along the way, autoboxing will convert a string to an object delegating to String.prototype if you write something like "hello".foobar(). But primitive value strings are not objects.
- NaN is just a number type . You have NaN in Java or C++ too. It's a way to represent "a number we can't represent"
- Good catch on strings, I'll edit it in.
Those are magical values from IEEE 754.
IEEE 754 is also the reason why there is a signed zero or why division by zero results in +/- Infinity.
>>> 0 === -0
true
>>> 1/0 === 1/-0 // compares Infinity with -Infinity
falseIt is not ever correct to say that null in JavaScript is an object. Just ask javaScript itself:
Object.getPrototypeOf(null)
//=> TypeError: Object.getPrototypeOf called on non-objecthttps://www.destroyallsoftware.com/talks/wat
(with a little bit of ruby)
Perhaps it would be worth to mention that 'new' not only sets 'this' to be the empty object but also return that object to the location where new was used.
Uh, how floating poing operators are different than this in C or java
Whether you like it or not js is here to stay. It's the language of the web (and more). A lot of new capabilities are being exposed via browser makers (e.g peerconnection, webrtc) which only serve to increase its power. Calling it stupid and ugly is your unsubstantiated opinion. (Infinitely more useful: say why this is your opinion.)
I think this is a nice intro to the language. Why it's being posted now though is a little puzzling considering it's from 2006. It is obviously still relevant and interesting but readers should realize it's not very recent.
* Overview: https://rawgithub.com/whatwg/html-differences/master/Overvie...
The next thing is JavaScript "next" or Ecma Script 6
* http://wiki.ecmascript.org/doku.php?id=harmony:proposals
You can use Traceur if you want to try out ES6 features today More info: https://github.com/google/traceur-compiler
These days there is a lot of things going on in the tooling section
Build: * Grunt: http://gruntjs.com/ - a lot of grunt- tasks at http://npmjs.org/ * Newest kid in town: https://github.com/gulpjs/gulp
Modulization and dependency management: * http://en.wikipedia.org/wiki/CommonJS * http://browserify.org/
In the same manner as assembler is here to stay. Assembler is "the language of the computer". Not that many people write assembler these days though, majority moved on to languages more suited to their needs.
"Hey, look, this is Jenna. You'll have to work with her for the next 10 years. She's hard to figure out and grumpy at times, but if you treat her right she'll play along. Actually if you get to know her, she can be a great asset."
"Don’t make idols for yourselves" is another old expression.