html текст
All interests
  • All interests
  • Design
  • Food
  • Gadgets
  • Humor
  • News
  • Photo
  • Travel
  • Video
Click to see the next recommended page
Like it
Don't like
Add to Favorites

Обзор ECMAScript 6, следующей версии JavaScript

Для начала, ликбез и несколько фактов:
  • ECMAScript — это официальный стандарт языка JavaScript (Слово JavaScript не могло быть использовано, потому что слово Java являлось торговой маркой компании Sun) Т.е. JavaScript — это имплементация стандарта ECMAScript.
  • TC39 — комитет, развивающий стандарт ECMAScript и принимающий решения по включению фич в него.
  • ECMAScript стандартов много. Самый популярный из них — ECMA-262.
  • ECMAScript 5 — последняя редакция стандарта ECMA-262 (утвержден в 2009 году).
  • Предыдущие версии стандарта ECMA-262 были (совсем старые не упоминаю):
    • ECMAScript 3 — поддерживается большинством браузеров (утвержден в 1999 году).
    • ECMAScript 4 — не принят в виду слишком радикальных изменений в стандарте. Позднее в июле 2008 году в урезанном варианте (но все же намного богаче, чем ECMAScript 3) вылился в новый проект ECMAScript Harmony.

  • ECMAScript 6 (кодовое имя ECMAScript.next) должен утвердиться до конца 2013 года.


Итак, что же нас ждет в новой версии JavaScript?



Блочная область видимости (block scope)


В текущей версии JavaScript присутствует функциональная область видимости. Это означает, что все переменные, объявленные c помощью ключевого слова var, будут видны в любом месте функции (даже если они объявлены внутри блока):

function f(a) {
   if (a < 0) {
      var i = 3;
   }

  console.log(i); // 3
}

f(-1)


В новой версии появится ключевое слово let, которое позволит объявлять переменные с блочной областью видимости:

function f(a) {
   if (a < 0) {
      let i = 3;
   }

   console.log(i); // ReferenceError: i is not defined
}

f(-1)


Значения параметров по умолчанию


В функциях добавилась возможность объявлять у параметров значения по умолчанию:

function setLevel(newLevel = 0) {
   ...
}

setLevel(); // newLevel = 0
setLevel(5); // newLevel = 5
setLevel(undefined); // newLevel = 0


Именованные параметры функций


В функциях также появилась возможность указывать именованные параметры:

function foo({ from, to = 10 }) {
   ...
}

foo({ from: 1, to: 5 });
foo({ to: 5, from: 1 });
foo({ from: 1 });


Именованные параметры можно комбинировать с обычным (позиционными параметрами):

function foo(positional, { named1, named2 }) {
   ...
}

foo(123, { named1: 'abc', named2: 'def' })
foo(123, { named2: 'def', named1: 'abc' })


Destructuring assignment


ECMAScript 6 позволит деструктуризировать при присваивании:

let { first: f, last: l } = { first: 'Jane', last: 'Doe' };
console.log(f); // 'Jane'
console.log(l); // 'Doe'


Кстати, в примере из предыдущего пункта (Именованные параметры) вы видели пример деструктуризации параметров функции.

Деструктуризация по умолчанию является refutable (не имею понятия, как это переводить). Т.е. если в объекте-источнике присваивания соответствующего поля нету, то выбрасывается ошибка:

let { first: f, last: l } = { first: 'Jane' };  // ошибка


Если же вы не хотите, чтобы ошибка генерировалась, то переменную можно объявить как irrefutable с помощью суффикса ?:

let { first: f, last?: l } = { first: 'Jane' };  // ok
console.log(l);  // undefined


Либо можно дать переменной значение по умолчанию:

let { first: f, last: l = 'Unknown' } = { first: 'Jane' };  // ok
console.log(l);  // 'Unknown'


Значение по умолчанию также срабатывает, если соответствующее поле в объекте-источнике является undefined:

let { a: x = 1 } = { a: undefined }
console.log(x);  // 1


Наконец, если вы хотите, чтобы все переменные были irrefutable, то можно поставить суффикс ? в конце всего шаблона присваивания:

let { foo: f }? = anything;  // всегда ok

В последнем примере переменная f будет инициализирована значением undefined, если anything будет равно undefined, null или не иметь поля foo.

С помощью деструктуризации можно одной строчкой кода поменять значение двух переменных (без всяких tmp):

{ foo: foo, bar: bar } = { foo: bar, bar: foo};


Или ище короче:

[ foo, bar ] = [ bar, foo ];


Классы


В ECMAScript 6 появятся классы:

// Supertype
class Person {
   constructor(name) {
      this.name = name;
   }

   describe() {
      return "Person called " + this.name;
   }
}

// Subtype
class Employee extends Person {
   constructor(name, title) {
      super.constructor(name);
      this.title = title;
   }

   describe() {
      return super.describe() + " (" + this.title + ")";
   }
}


Теперь можно использовать эти классы:

let jane = new Employee("Jane", "CTO");
jane instanceof Person; // true
jane instanceof Employee; // true
jane.describe(); // 'Person called Jane (CTO)'


Всего того же можно было добиться с помощью прототипов:

// Supertype
function Person(name) {
   this.name = name;
}

Person.prototype.describe = function () {
   return "Person called " + this.name;
};

// Subtype
function Employee(name, title) {
   Person.call(this, name);
   this.title = title;
}

Employee.prototype = Object.create(Person.prototype);
Employee.prototype.constructor = Employee;
Employee.prototype.describe = function () {
   return Person.prototype.describe.call(this) + " (" + this.title + ")";
};


Как видите, классы в ECMAScript 6 — это просто синтаксический сахар над конструкторами и функциями.

Классы могут иметь статические методы:

class Point {
   constructor(x, y) {
      this.x = x;
      this.y = y;
   }
   
   static zero() {
      return new Point(0, 0);
   }
}


Приватных полей и методов не будет (по крайней мере, в ECMAScript 6). Однако некоторое сокрытие данных все же появится. Через модули.

Модули


В JavaScript наконец-то появятся модули:

module Math {
   export function sum(x, y) {
      return x + y;
   }

   export var pi = 3.141593;

   // Не видна снаружи
   function internal() {
      ...
   }
}


Импортирование модуля:

import Math.{sum, pi}; 
alert("2π = " + sum(pi, pi));


Можно использовать *, чтобы импортировать всё:

import Math.*; 
alert("2π = " + sum(pi, pi));


Модули можно вкладывать друг в друга:

module Widgets {
   module Button { ... }
   module Alert { ... }
   module TextArea { ... }
   ...
}

import Widgets.Alert.{messageBox, confirmDialog};
...


Модули можно подгружать из веба или через файловую систему:

module JSON = require('http://json.org/modules/json2.js'); // web
import JSON.*;

module File = require('io/File'); // file system

import require("bar.js").y; // file system


Все глобальные переменные в модули являются глобальными только в этом модуле.

Возможны циклические зависимости между модулями.

Цикл for-of


Как вы знаете, цикл for-in в JavaScript итерирует по всем полям объекта (включая наследованных). Т.е. итерироваться по значениям массива можно, но опасно:

let arr = [ "blue", "green" ];
arr.notAnIndex = 123;
Array.prototype.protoProp = 456;

for(var x in arr) {
   console.log(x); // Напечатает blue, green, notAnIndex, protoProp
}


В ECMAScript 6 появится цикл for-of, который решит данную проблему:

for(var x of arr) {
   console.log(x); // Напечатает только blue, green
}


Также, возможно, в язык добавится оператор yield, с помощью которого можно легко и красиво писать кастомные итераторы.

Arrow-функции


В ECMAScript 6 появятся arrow functions:

let squares = [ 1, 2, 3 ].map(x => x * x);


Код выше эквивалентен этому:

let squares = [ 1, 2, 3 ].map(function (x) { return x * x });


Arrow-функции немножко отличаются от обычных функций. В первую очередь тем, что в arrow-функциях this привязан к вышестоящему контексту. Т.е.

let jane = {
   name: "Jane",
        
   sayHello: function (friends) {
      friends.forEach(friend => { console.log(this.name + " says hello to " + friend) });
   }
}

jane.sayHello([ 'Mark', 'John' ]);

выведет
Jane says hello to Mark
Jane says hello to John

как и ожидалось. А

let jane = {
   name: "Jane",
        
   sayHello: function (friends) {
      friends.forEach(function(friend) { console.log(this.name + " says hello to " + friend) });
   }
}

выведет:
 says hello to Mark
 says hello to John


Проблема в том, что this из анонимной функции function(friend) { ... }) перекрывает this из окружающего контекста. Для того, чтобы этого избежать, можно использовать старый прием с var self = this или использовать функцию bind:

var jane = {
   name: "Jane",
        
   sayHello: function (friends) {
      friends.forEach(function (friend) {
         console.log(this.name + " says hello to " + friend)
       }.bind(this));
   }
}


Т.е. по сути своей arrow functions — опять же синтаксический сахар над существующими анонимными функциями:

(x, y) => x + y + this.z


есть ничто иное как:

function (x, y) { return x + y + this.z }.bind(this)


Другие отличия arrow-функций от обычных функций:
  • Нельзя использовать arrow-функции как конструкторы (new (() => {}) кинет ошибку)
  • Arrow-функции не могут обратиться к переменной arguments (да и незачем)


В остальном arrow-функции не отличаются от обычных функций. Они поддерживают значения по умолчанию, переменное количество параметров, операторы typeof и instanceof:

typeof () => {}; // 'function'
() => {} instanceof Function; // true


Заключение


Я описал далеко не всё, что появится в новом стандарте ECMAScript 6. И очень возможно, что что-то из того, о чем я написал выше, может измениться или вообще не появиться в стандарте. Тем не менее, все, что я описал, — это не слухи. Это вещи, реально обсуждаемые комитетом TC39. И к концу этого (2013) года стандарт должен быть утвержден.

Ссылки


Большая часть информации взята из блога доктора Axel'а Rauschmayer'a, послушать которого и повидать вживую мне посчастливилось на конференции CodeFest в Новосибирске.

PS. Спасибо 2GIS за организацию конференции!
Читать дальше
Twitter
Одноклассники
Мой Мир

материал с habrahabr.ru

0

      Add

      You can create thematic collections and keep, for instance, all recipes in one place so you will never lose them.

      No images found
      Previous Next 0 / 0
      500
      • Advertisement
      • Animals
      • Architecture
      • Art
      • Auto
      • Aviation
      • Books
      • Cartoons
      • Celebrities
      • Children
      • Culture
      • Design
      • Economics
      • Education
      • Entertainment
      • Fashion
      • Fitness
      • Food
      • Gadgets
      • Games
      • Health
      • History
      • Hobby
      • Humor
      • Interior
      • Moto
      • Movies
      • Music
      • Nature
      • News
      • Photo
      • Pictures
      • Politics
      • Psychology
      • Science
      • Society
      • Sport
      • Technology
      • Travel
      • Video
      • Weapons
      • Web
      • Work
        Submit
        Valid formats are JPG, PNG, GIF.
        Not more than 5 Мb, please.
        30
        surfingbird.ru/site/
        RSS format guidelines
        500
        • Advertisement
        • Animals
        • Architecture
        • Art
        • Auto
        • Aviation
        • Books
        • Cartoons
        • Celebrities
        • Children
        • Culture
        • Design
        • Economics
        • Education
        • Entertainment
        • Fashion
        • Fitness
        • Food
        • Gadgets
        • Games
        • Health
        • History
        • Hobby
        • Humor
        • Interior
        • Moto
        • Movies
        • Music
        • Nature
        • News
        • Photo
        • Pictures
        • Politics
        • Psychology
        • Science
        • Society
        • Sport
        • Technology
        • Travel
        • Video
        • Weapons
        • Web
        • Work

          Submit

          Thank you! Wait for moderation.

          Тебе это не нравится?

          You can block the domain, tag, user or channel, and we'll stop recommend it to you. You can always unblock them in your settings.

          • habrahabr.ru
          • домен habrahabr.ru

          Get a link

          Спасибо, твоя жалоба принята.

          Log on to Surfingbird

          Recover
          Sign up

          or

          Welcome to Surfingbird.com!

          You'll find thousands of interesting pages, photos, and videos inside.
          Join!

          • Personal
            recommendations

          • Stash
            interesting and useful stuff

          • Anywhere,
            anytime

          Do we already know you? Login or restore the password.

          Close

          Add to collection

             

            Facebook

            Ваш профиль на рассмотрении, обновите страницу через несколько секунд

            Facebook

            К сожалению, вы не попадаете под условия акции