JavaScript. Подробное руководство, 6-е издание
8.7.1. Свойство length
В теле функции свойство
определяет количество аргументов, переданных функции. Однако свойство<b>arguments.length</b>самой функции имеет иной смысл. Это свойство, доступное только для чтения, возвращает количество аргументов, которое функция ожидает получить, - число объявленных параметров.<b>length</b>В следующем фрагменте определяется функция с именем
получающая массив аргументов<b>check(),</b>от другой функции. Она сравнивает свойство<b>arguments</b>(число фактически переданных аргументов) со свойством<b>arguments.length</b>(число ожидаемых аргументов), чтобы определить, передано ли функции столько аргументов, сколько она ожидает. Если значения не совпадают, генерируется исключение. За функцией<b>arguments. callee.length</b>следует тестовая функция<b>check()</b>, демонстрирующая порядок использования функции<b>f()</b><b>check():</b><b>// Эта функция использует arguments.callee, поэтому она </b><b>// не будет работать в строгом режиме, </b><b>function check(args) {</b><b> var actual = args.length; // Фактическое число аргументов</b><b> var expected = args.callee.length; // Ожидаемое число аргументов </b><b> if (actual !== expected) // Если не совпадают, генерируется исключение</b><b> throw new Еrror("ожидается: " + expected + получено " + actual);</b><b>}</b><b>function f(x, у, z) {</b><b> // Проверить число ожидаемых и фактически переданных аргументов. </b><b> check(arguments);</b><b> // Теперь выполнить оставшуюся часть функции как обычно </b><b> return х + у + z;</b><b>}</b>8.7.2. Свойство prototype
Любая функция имеет свойство prototype, ссылающееся на объект, известный как объект прототипа. Каждая функция имеет свой объект прототипа. Когда функция используется в роли конструктора, вновь созданный объект наследует свойства этого объекта прототипа. Прототипы и свойство prototype обсуждались в разделе 6.1.3, и мы еще раз вернемся к этим понятиям в главе 9.
8.7.3. Методы call() и apply()
Методы
и<b>саll()</b>позволяют выполнять косвенный вызов функции (раздел 8.2.4), как если бы она была методом некоторого другого объекта. (Мы уже использовали метод<b>аррlу()</b>в примере 6.4 для вызова<b>саll()</b>относительно объекта, класс которого необходимо было определить.) Первым аргументом обоим методам,<b>Object.prototype.toString </b>и<b>саll()</b>передается объект, относительно которого вызывается функция; этот аргумент определяет контекст вызова и становится значением ключевого слова<b>аррlу(),</b>в теле функции. Чтобы вызвать функцию<b>this</b>(без аргументов) как метод объекта о, можно использовать любой из методов,<b>f()</b>или<b>саll()</b><b>аррlу():</b><b>f.call(о); </b><b>f.apply(o);</b>Любой из этих способов вызова эквивалентен следующему фрагменту (где предполагается, что объект о не имеет свойства с именем m):
<b>о.m = f; // Временно сделать f методом о. </b><b>о.m(); // Вызывать его без аргументов,</b><b>delete о.m; // Удалить временный метод.</b>В строгом режиме ECMAScript 5 первый аргумент методов
и<b>саll()</b>становится значением<b>apply()</b>, даже если это простое значение,<b>this</b>или<b>null</b>. В ECMAScript 3 и в нестрогом режиме значения<b>undefined</b>и<b>null</b>замещаются глобальным объектом, а простое значение - соответствующим объектом-оберткой.<b>undefined</b>Все остальные аргументы метода
следующие за первым аргументом, определяющим контекст вызова, передаются вызываемой функции. Например, ниже показано, как можно передать функции<b>саll(),</b>два числа и вызвать ее, как если бы она была методом объекта о:<b>f()</b><b>f.call(o, 1, 2);</b>Метод
действует подобно методу<b>аррlу()</b>за исключением того, что аргументы для функции передаются в виде массива:<b>саll(),</b><b>f.apply(o, [1,2]);</b>Если функция способна обрабатывать произвольное число аргументов, метод
может использоваться для вызова такой функции в контексте массива произвольной длины. Например, чтобы отыскать наибольшее число в массиве чисел, для передачи элементов массива функции<b>apply()</b>можно было бы использовать метод<b>Math.max()</b><b>ар ply ():</b><b>var biggest = Math.max.apply(Math, array_of_numbers);</b>Обратите внимание, что метод
может работать не только с настоящими массивами, но и с объектами, подобными массивам. В частности, вы можете вызвать функцию с теми же аргументами, что и текущую функцию, передав массив с аргументами непосредственно методу<b>apply()</b>Этот прием демонстрируется ниже:<b>аррlу().</b>