Ответ 1
a = a || function(){...}
- это идиома, которая очень распространена в Javascript. Он опирается на два понятия, которые, хотя и не являются уникальными для Javascript, вы, возможно, еще не знакомы.
1. Короткое замыкание оператора
Оператор короткого замыкания [wikipedia] - это оптимизация компилятора, которая была изобретена для предотвращения ненужной оценки.
Чтобы продемонстрировать это, давайте предположим, что мы хотим определить, является ли человек подростком: то есть, имеет ли человек возраст от 13 до 19 лет.
var isTeenager = person.age >= 13 && person.age <= 19;
Теперь предположим, что код выполняется, и оказывается, что человек моложе 13. Первое условие будет оценено и вернет false. Поскольку теперь программа знает, что левая часть оператора &&
равна false
, и поскольку &&
требует, чтобы обе стороны были true
, чтобы оценить значение true
, он знает, что оценка права сторона стороны бессмысленна.
Такой же принцип применяется к оператору ||
. Предположим, мы хотели узнать, может ли человек бесплатно ездить на автобусе: если человек старше 70 лет или инвалид.
var canRideFree = person.age >= 70 || isHandicapped(person);
Если человек старше 70 лет, программа уже знает, что он может ехать бесплатно. На данный момент программе все равно, если он инвалид или нет, и поэтому не оценивает вызов функции isHandicapped
. Если, с другой стороны, человек был моложе 70, тогда canRideFree
будет установлен на все isHandicapped
.
2. Значения правды и ложности
Значения truthy и falsy [некоторый случайный блог] - это логические оценки объектов. В Javascript каждый объект будет оценивать либо "правдивое", либо "ложное" значение.
Выражение является "ложным", если его значением является любое из них:
false, null, undefined, 0, "", NaN
Все остальное правдиво.
Люди используют тот факт, что переменная null или undefined имеет значение false
. Это означает, что вы можете проверить, существует ли переменная очень просто:
if (a) { /* a exists and is not a falsy value */ }
Объединяя то, что мы знаем
Короткие замыкания оператора ||
и возвращает значение последнего выражения, которое оно оценивает. Этот принцип сочетается с правдивостью в этом единственном утверждении:
Object.keys = Object.keys || function() {...}
Если Object.keys
является правдивым, оно будет оцениваться и присваиваться самому себе. В противном случае функции Object.keys
будут назначены функции. Это очень распространенная идиома в Javascript для проверки того, существует ли уже существующее значение и присваивает ему что-то еще, если это не так.
Некоторые другие языки, такие как С#, которые не имеют правдоподобия, имеют оператор с нулевой связностью [MSDN], который имеет аналогичную цель.
object Value = PossiblyNullValue ?? ValueIfNull;
В этом коде Value
будет присвоен PossiblyNullValue
, если он не равен нулю, и в этом случае ему будет присвоено значение ValueIfNull
.
tl; dr [wikipedia]
Если вы не удосужились прочитать что-либо, о чем я сказал выше, все, что вам нужно знать, это то, что a = a || function() {...}
в основном делает то, что делает этот код:
if (exists(Object.keys)) {
Object.keys = Object.keys;
} else {
Object.keys = function() {...};
}
function exists(obj) {
return typeof obj !== "undefined" &&
obj !== null &&
obj !== false &&
obj !== 0 &&
obj !== "" &&
!isNaN(obj);
}