Introduction, test cases and web browser compatibility tables for JavaScript 1.6, JavaScript 1.7 & JavaScript 1.8
Lately I’ve been investigating newer versions of JavaScript, and what web browser support they have. And, as usual when I create something I find useful, I want to share it with the world. 🙂
How JavaScript has evolved
Web development life for most of us is based on JavaScript 1.5, or corresponding support in JScript for IE and ECMAScript 3 (more info can be found in John Resig’s Versions of JavaScript). But what’s beyond that? Mozilla, especially due to having JavaScript creator Brendan Eich on board, have been pushing JavaScript feature support forward.
I have looked at the three latest issued releases of JavaScript: 1.6, 1.7 and 1.8, tested the code in various web browsers and evaluated the results.
The JavaScript tests and compatibility tables
For this, I’ve created a mini-web site for JavaScript testing and web browser compatibility, which offers you:
- JavaScript tests which runs immediately in your web browser
- Web browser compatibility tables
- Code examples, together with expected results (when tests were successful)
It currently contains three sub-sections for each version of JavaScript:
It should also be noted, for anyone looking for support in Internet Explorer, that neither IE 6, IE 7 or IE 8 supports anything of this…
Below I will list the new features for each JavaScript language release of these three, and code examples. All of this code, runnable, is also available in the test site, but listed here for convenience for anyone who wants to get a overview of the new features.
JavaScript 1.6
- Array extras
- indexOf
- lastIndexOf
- every
- filter
- forEach
- map
- some
- Array and String generics
- Array generics
- String generics
(For complete information and documentation, read New in JavaScript 1.6.)
Array extras
New features to enhance the usability of array
objects.
The indexOf method
Returns the index of the first occurrence of the item.
var arr = ["Microsoft", "Mozilla", "Apple"]; arr.indexOf("Mozilla");
The lastIndexOf method
Returns the index of the last occurrence of the item.
var arr = ["Firefox", "IE", "Chrome", "Firefox"]; arr.lastIndexOf("Firefox");
The every method
Runs a function on each item in the Array
, while it returns true.
var arr = [4, 7, 10]; arr.every(function (value) { return value > 5; });
var arr = [6, 7, 10]; arr.every(function (value) { return value > 5; });
The filter method
Runs a function to filter an Array
, and returns all items where the function returned true.
var arr = [4, 7, 10]; arr.filter(function (value) { return value > 5; });
The forEach method
Runs a function on each item in an array
.
var arr = ["Firefox", "IE", "Chrome", "Opera", "Safari"] resultValues = []; arr.forEach(function (value) { resultValues.push(value.toUpperCase()); });
The map method
Runs a function on each item, and returns the results in an array
.
var arr = [4, 7, 10]; arr.map(function (value) { return value + 5; });
The some method
Runs a function on each item in the Array
, while it returns false.
var arr = [4, 7, 10]; arr.some(function (value) { return value > 5; });
var arr = [1, 2, 4]; arr.some(function (value) { return value > 5; });
Array and String generics
Using methods from other object types to enhance the existing one. I.e. use String
methods on Array
objects, and Array
methods on String
objects.
Array generics
var words = "These are just words"; Array.filter(words, function (value) { return value.indexOf("s") === -1; });
String generics
var arr = ["Firefox", "Safari", "Opera"]; String.replace(arr, /[aoueiy]/g, "");
JavaScript 1.7
- Generators and Iterators
- Generators
- Iterators
- Array comprehensions
- Using let for block scope
- let statement
- let expression
- let definition
- Destructuring assignment
- Destructuring assignment with let statement
(For complete information and documentation, read New in JavaScript 1.7.)
Generators and Iterators
Helper features for iterating over items.
Generators
Creating generator iterators with the yield
keyword, to have state variables.
function double5() { var i=0, j=5, k; while (true) { yield i; k = i; i = j; j += i; } } var g = double5(), resultValues = []; for (var i=0; i<5; i++) { resultValues.push(g.next()); }
Iterators
A special object making it easier to iterate over a certain amount of informatÃon.
var lostInfo = { name : "Lost", location : "Island", numbers : "4 8 15 16 23 42" }; var iteratorObj = Iterator(lostInfo), resultValues = [], next; try{ while (true) { next = iteratorObj.next(); resultValues.push(next[0] + ": " + next[1]); } } catch (err if err instanceof StopIteration) { resultValues.push("END OF LIST"); } catch (err) { resultValues.push("UNKNOWN ERROR"); }
var lostInfo = { name : "Lost", location : "Island", numbers : "4 8 15 16 23 42" }; // Notice true below - will return only parameter names and not values, as opposed to the example above var iteratorObj = Iterator(lostInfo, true), resultValues = []; try{ while (true) { resultValues.push(iteratorObj.next()); } } catch (err if err instanceof StopIteration) { resultValues.push("END OF LIST"); } catch (err) { resultValues.push("UNKNOWN ERROR"); }
Array comprehensions
Powerful initialization of arrays.
function setVal (start, end) { for (let i=start; i<end; ++i) { yield i; } } var evenValues = [i for each (i in setVal(0, 15)) if (i % 2 == 0)];
Using let for block scope
Connecting certain variables with statements or blocks, effectively creating block scope variables.
let statement
var x = 5, y = 7, resultValues = ["Before let statement: " + x + ", " + y]; let (x=15, y=12) { resultValues.push("In let statement: " + x + ", " + y); } resultValues.push("After let statement: " + x + ", " + y);
let expression
var x = 1, y = 3, resultValues = ["Before let expression: " + x + ", " + y]; let (x=7, y=8) resultValues.push("In let expression: " + x + ", " + y); resultValues.push("After let expression: " + x + ", " + y);
let definition
var letDefinitionResults = document.getElementById("results-let-definition"), item; for (var i=0; i<5; i++) { item = document.createElement("div"); item.innerHTML = "Click me - I will say " + i; let j = i; item.onclick = function () { alert("I am " + j); }; letDefinitionResults.appendChild(item); }
Destructuring assignment
Allows you to get data from array
s, and swap values between various array
objects.
var a = 1, b = 2; // Value swapping [a, b] = [b, a];
var a = 1, b = 2, c = 3, d = 4; // Value swapping [a, b, c, d] = [d, c, b, a];
var a = 1, b = 2; function newValues () { return [10, 20]; } // Assigning new values [a, b] = newValues();
var a = 1, b = 2; function newValues () { return [10, 20, 30]; } // Assigning new values, ignoring the second one [a, , b] = newValues();
Destructuring assignment with let statement
Destructirung assignments can get even more powerful in conjunction with let
statements.
var griffins = { father : "Peter", mother : "Lois", son : "Chris", daugher : "Meg", baby : "Stewie", dog : "Brian" }, resultValues = []; for (let [type, name] in Iterator(griffins)) { resultValues.push(type + ": " + name); }
JavaScript 1.8
- Expression closures
- Generator expressions
- Array extras
- reduce
- reduceRight
(For complete information and documentation, read New in JavaScript 1.8.)
Expression closures
Basically, just a shorthand notation for functions.
// Notice the omission of braces and return statement function expressionClosure () "Yeah, ok"
Generator expressions
Using generator expressions to complement generators introduced in JavaScript 1.7.
var animals = { dog : "Nice", cat : "Independent", horse : "big" }, resultValues = [], iterating = (i + 3 for (i in animals)); try { while (true) { resultValues.push(iterating.next()); } } catch (err if err instanceof StopIteration) { resultValues.push("END OF LIST"); }
Array extras
reduce
Runs on each item in the array
, collecting the results from the previous iteration.
var numbers = [1, 2, 3, 4, 5], returnValues = []; numbers.reduce(function (prev, current, index, array) { returnValues.push("Previous: " + prev + ", current: " + current + ", index: " + index); return current; });
reduceRight
Runs on each item in the array
, collecting the results from the previous iteration, but in reverse order.
var numbers = [1, 2, 3, 4, 5], returnValues = []; numbers.reduce(function (prev, current, index, array) { returnValues.push("Previous: " + prev + ", current: " + current + ", index: " + index); return current; });
My own takes
Personally, I’m very excited by new features being introduced to JavaScript, and especially some of them (like the let
statement) will change and simplify a lot of code. It’s good to see a number of the other web browsers vendors being aboard with at least some of the features, although (as usual) it’s disheartening to see that Internet Explorer has effectively not gotten any of these features…
Great job Robert!
Thanks for sharing the collected info with World 🙂
Nice ads: http://bayimg.com/FaPADaabF 🙂
And great write up!
Morgan,
Thanks!
Andreas,
Yes, custom-bought ads… 😉
And thank you!
Robert, I plan to include some Javascript 1.6 array extras into the next version of DOMAssistant.
Methods planned for are indexOf, map, filter, some and every. Hopefully it will be a useful equalizer for developing for IE!
chenghong,
Sounds great! 🙂
The Array extra's and generics can easily be implemented crossbrowser: Crossbrowser Array Generics
Tino,
Thanks for the addition!
[…] Introduction, test cases and web browser compatibility tables for JavaScript 1.6, JavaScript 1.7 &am… […]
[…] by the dollar function $ is essentially an array, so naturally we should be able to use the snazzy Javascript 1.6 array extras on them. Well, except one thing: not all browsers are created equal. DOMAssistant attempts to fill […]
[…] Introduction to the tests […]
Robert,
Nice work. However, you didn’t mention anything about ECMAScript 5. This is the new standard for JavaScript that is already strongly influecing browser JavaScript implementations (for example Object.defineProperty is directly taken from ES5).
You may also be interested in the comformance test suite that is being developed to test ES5 implementations.
Allen Wirfs-Brock
Microsoft
No Opera versions correctly support destructuring. The most Opera supports is <code>[a,b] = [b,a]</code> and not much more.
To be considered supporting destructuring, this last line of this code should be true:
<code>
function foo({a, b:c, d:[e, f]}, [g, h], [{i:j}]) {
return a+c+e+f+g+h+j;
};
foo({a:1, b:2, d:[3, 4]}, [5, 6], [{i:7}]) === 28
</code>
The fact that IE doesn't support JS 1.6-1.8 really makes them unusable in the mainstream for years to come. That's really too bad…
Also, E4X is part of JavaScript 1.6 so I think you should include it in the compatibility tables too.
Elijah,
You are correct. Opera only has partial destructuring support and I have added that information to my tests.
Regarding E4X is an interesting idea, and I initially considered that. Haven't got around to it, but it will most likely be added in the future.
Thanks for the suggestion!
Dan,
It is not to good, I agree. However, I'm glad they support DOM Storage and native JSON, though!
Allen,
Thank you! ECMAScript 5 is indeed very exciting, and it's good to see how it inspires web browser vendors. I will, most likely, have parts of it in future versions of the test.
Also, thanks for the link to the test suite.
the test "native JSON" is successfull for Google Chrome 2
you may update the compatibility table
Zmitro,
In the latest official version of Google Chrome, version 2.0.172.31, it is not supported. It might be there in upcoming versions, though, and then I will update the compatibility table.
[…] Introduction to the tests […]
Great work, thanks!
Note: Test code for <code>reduce</code> and <code>reduceRight</code> seems to be absolutely identical :)?
Svitlana,
Thank you, glad you like it!
The test for <code>reduceRight</code> was being run correctly, but the written code in the page only displayed <code>reduce</code>. I have fixed that now! Thanks!
[…] 27: Introduction, test cases and web browser compatibility tables for JavaScript 1.6, JavaScript 1.7 �… […]