Внимание! Прочитайте, пожалуйста, текст в правой колонке (внизу).
Внимание! Прочитайте, пожалуйста, текст в правой колонке (внизу). Внимание! Прочитайте, пожалуйста, текст в правой колонке (внизу). Homepage Карта сайта Версия для печати

Джентльменский набор Web-разработчика   Ларри Уолл о Perl6   Наблы Система Orphus
 

38. Маленькие хитрости JavaScript, или пишем скрипты по-новому

[5 марта 2004 г.] обсудить статью в форуме

Вполне возможно, что после этой и следующей наблы вы почувствуете себя глупо. Вы будете ощущать себя так же, как программист для Windows, всю жизнь рисовавший круги, прямоугольники, кнопки и т. д. вручную (по точкам — например, через DirectDraw), и вдруг обнаруживший, что в этой ОС существует куча готовых средств для отрисовки элементов интерфейса.

Признаюсь честно, полгода я сам чувствовал себя точно так же. Началось все с того, что я случайно заглянул в XUL-файлы платформы Mozilla (там хранится код, заведующий некоторыми интерфейсными элементами браузера). Код, который я увидел, выглядел несколько странно и необычно. Это какой вообще язык? Оказалось, что JavaScript, и при том самый обыкновенный. Но я никогда не писал так, и не видел, чтобы кто-то еще это делал!

JavaScript и Perl

Как вы думаете, на какой другой язык программирования больше всего похож JavaScript? Если вы считаете, что это Java или C++, то ошибаетесь. Наиболее близкий к JavaScript язык (по идеологии) — это... Perl. Да-да, вы не ослышались. Perl — ближайший «соратник» JavaScript, и в данной статье я покажу это на примерах.

Прежде, чем заняться сложными вещами, вот вам несколько трюков, которые можно использовать при программировании на JavaScript (и синтаксис которых очень напоминает Perl).

Операторы || и &&

Как и в Perl, в JavaScript можно применять эти полезные операторы не только в логическом контексте, а, например, и в таких случаях:

Листинг 1
// Значения по умолчанию.
function hello(text) {
  alert("Hello, " + (text||"world"));
}

// Не выдает ошибку в случае отсутствия одного из ключей.
// Если же все на месте, присвоит переменной значение
// h['x']['y'], иначе - null.
var element = h && h['x'] && h['x']['y'];

Оператор || возвращает свой второй аргумент, если первый оказался «ложным» (false, null, "", 0), и первый — в противном случае. Оператор && возвращает свой второй аргумент, если первый оказался истинным, и первый — если ложным.

К сожалению, оператор ||=, столь популярный в Perl, в JavaScript не поддерживается.

Хэши

Возможно, вы слышали, что любая переменная в JavaScript — это на самом деле объект. Не важно, число это или строка. Например, можно написать:

Листинг 2
var part = "Matrix has you".substr(0, 6);
var a = 10;
var b = a.toString(); // конечно, это 10
alert(typeof 10);     // выводит "Number"

Но что представляет собой объект? Как ни странно, любой объект выглядит в программе как хэш. Да-да, тот самый хэш, который есть и в языке Perl. И создается он точно таким же оператором, только вместо => используется двоеточие:

Листинг 3
var hash = {
  color:    "red",
  artefact: "pill",
  actors: {
    supplier: "Morpheus",
    consumer: "Neo"
  }
}

Чайник 

Обратите внимание на две вещи. Во-первых, ставить ; в конце не обязательно: в JavaScript точка с запятой — вообще необязательный символ, вместо нее может служить и конец строки. Во-вторых, лишние запятые после } не допускаются (в отличие от C++, Perl, PHP).

Свойства (и методы, кстати, тоже) объекта — это просто элементы хэша. Для обращения к ним можно использовать две разновидности синтаксиса:

Листинг 4
var element1 = hash.element;
var element2 = hash['element'];

А вот теперь — внимание: эти два способа полностью идентичны! Нет никакой разницы, обращаетесь ли вы к хэшу как hash.element или как hash['element']. Зачем же тогда нужен второй вариант? Нетрудно догадаться: мы можем не знать в явном виде имя ключа, к которому хотим обратиться:

Листинг 5
var key = "element";
var element1 = hash.key;  // полная ерунда
var element2 = hash[key]; // а вот так - правильно

Хэши можно создавать и поэлементно:

Листинг 6
var hash = new Object(); // Object - это и есть хэш.
hash.color = "blue";
hash.element = "pill";

Ключи хэша, конечно, могут представлять из себя и обычное число:

Листинг 7
var hash = {
  10: 'input x',
  20: 'print "Hello, ", x'
}
alert(hash[10]);

Чайник 

Тем не менее, выражение hash.0 вместо hash[0] не работает (хотя IE иногда имеет обыкновение показывать такие сообщения об ошибке:
Попытка выполнить alert(hash[0].x)

Массивы

Последние примеры наводят на правильную догадку о природе массивов в JavaScript. Да, действительно, массивы — это обыкновенные хэши с числовыми ключами, а также ключом length, содержащим их длину.

Лирическое отступление 
На самом деле это не совсем так, потому что команды for (var k in arr) alert(k) выводят лишь числовые ключи массива, но не свойство length. Тем не менее, в первом приближении гипотезу о происхождении массивов вполне можно принять.

Массивы в JavaScript создаются оператором [] (заметьте, опять аналогия с Perl):

Листинг 8
var arr = [100, 200, 300];
for (var k in arr) alert(k + "=>" + arr[k]);
alert("length: "+arr.length);

Распечатка

Если попытаться распечатать весь массив командой alert(arr), то будут отображены все его элементы. Это достаточно удобный трюк, если в отладочных целях надо вывести значения нескольких переменных, но лень писать плюсики и запятые в кавычках:

Листинг 9
// Можно и так...
alert(status+","+location+","+navigator.appName);
// Но следующий код смотрится явно лучше:
alert([status, location, navigator.appName]);

Команда вроде alert([1,2,[4,5],6]), как это ни печально, выводит все элементы массива в кучу, не обращая внимания на вложенность.

К сожалению, распечатать хэш таким способом не получится: будет выведена строка [object Object] (точный вид зависит от браузера). Для того, чтобы все-таки отлаживать программы со сложными хэшами, я написал следующую функцию:

Листинг 10
function Dump(d,l) {
    if (l == null) l = 1;
    var s = '';
    if (typeof(d) == "object") {
        s += typeof(d) + " {\n";
        for (var k in d) {
            for (var i=0; i<l; i++) s += "  ";
            s += k+": " + Dump(d[k],l+1);
        }
        for (var i=0; i<l-1; i++) s += "  ";
        s += "}\n"
    } else {
        s += "" + d + "\n";
    }
    return s;
}

В следующей набле мы поговорим о более сложных вещах — о замыканиях и объектно-ориентированном программировании в JavaScript.

обсудить статью в форуме

 
Рекламный блок
   

На странице:
    38. Маленькие хитрости JavaScript, или пишем скрипты по-новому
JavaScript и Perl
Операторы || и &&
Хэши
Массивы
Распечатка

Важное объявление:
    автор категорически против копирования и распространения в Интернете всех статей «Куроводства» с возрастом, меньшим 6 месяцев. Печальный опыт «расползания» чрезвычайно устаревших ошибочных версий статьи про Apache действительно объясняет такое решение.

Орфография на «Куроводстве»:
    если вы заметили орфографическую, стилистическую или другую ошибку на этой странице, просто выделите ошибку мышью и нажмите Ctrl+Enter. Выделенный текст будет немедленно отослан вебмастеру, а Вы даже ничего и не заметите — настолько быстро все произойдет.

На заметку:
    если вы уже вскипели насчет дизайна этой страницы, то присмотритесь повнимательнее к названию, почитайте FAQ, сходите по лебедевским местам, как это уже предлагалось выше. Можно ли считать пародию плагиатом? Надеюсь, что нет.

Параметры этой страницы
   
GZip

Ссылки от спонсоров
   


Дмитрий Котеров | 5 марта 2004 г. ©1999-2016 | Генеральный спонсор: Хостинг «Джино» | Контакт Вернуться к оглавлению