Функции Javascript
Функция JavaScript это блок кода, предназначенный для выполнения определенной задачи. По сути функции JavaScript это то же самое, что и процедуры или подпрограммы в других языках программирования.
Функция JavaScript выполняется только тогда, когда «что-то» обращается к ней (вызывает ее).
function myFunction(p1, p2) < return p1 * p2; // Эта функция возвращает производное p1 и p2 >
Синтаксис функции JavaScript
Функция JavaScript декларируется при помощи ключевого слова function, за которым следует имя и круглые скобки ().
Имя функции может состоять из букв, цифр, символа подчеркивания и символа доллара (те же правила, что и с переменными).
Внутри круглых скобок могут определяться имена параметров, разделенных запятыми: (параметр1, параметр2, . ).
Исполняемый код функции помещается внутри фигурных скобок <>:
function имя(параметр1, параметр2, параметр3)
Параметры функции перечисляются внутри круглых скобок () в заголовке функции.
Аргументы функции это значения, получаемые функцией при ее вызове.
Внутри функции аргументы (параметры) ведут себя как локальные переменные.
Вызов функции
Код внутри функции выполняется только тогда, когда «что-то» обращается к ней (вызывает ее):
- Когда возникает некое событие (например, пользователь нажимает на кнопку)
- Когда функция вызывается из JavaScript кода
- Автоматически (самовызов)
Подробнее обо всем этом будет рассказано дальше в этом учебнике.
Возвращение результата из функции
Когда интерпретатор JavaScript достигает выражения return, функция прекращает выполняться.
Если функция была вызвана из кода, интерпретатор вернет выполнение коду, расположенному после вызвавшего функцию выражения.
Часто функции возвращают некое значение, которое они вычисляли. Возвращенное значение «возвращается» обратно тому, кто ее вызвал.
Вычислим произведение двух чисел и вернем результат:
// Вызывается функция, возвращаемое значение // сохраняется в переменной x var x = myFunction(4, 3); function myFunction(a, b) < return a * b; // Функция возвращает произведение от a и b >
В результате в переменной x будет получено значение 12.
Зачем нужны функции?
Функции позволяют повторно использовать код: однажды определите некий блок кода и затем используйте его сколько угодно раз из любого места скрипта.
Вы можете использовать один и тот же код много раз с разными аргументами, чтобы получить разные результаты.
В следующем примере используется функция, конвертирующая градусы Фаренгейта в градусы Цельсия:
function toCelsius(fahrenheit) < return (5/9) * (fahrenheit-32); >document.getElementById("demo").innerHTML = toCelsius(77);
Оператор () вызывает функцию
Если брать пример кода, приведенный ранее, то выражение toCelsius обращается к объекту функции, а выражение toCelsius() к результату функции.
Вызов функции без скобок () вернет определение функции, а не результат ее работы:
function toCelsius(fahrenheit) < return (5/9) * (fahrenheit-32); >document.getElementById("demo").innerHTML = toCelsius;
Функции как значения переменных
Функции могут использоваться так же как переменные во всех типах формул, в операторах присваивания и в любых вычислениях.
Вместо использования переменной для хранения результата функции:
var x = toCelsius(77); var text = "Температура - " + x + " градусов Цельсия";
Вы можете использовать саму функцию, как значение переменной:
var text = "Температура - " + toCelsius(77) + " градусов Цельсия";
Подробнее о функциях будет рассказано в следующих главах этого учебника.
#10 – Функции в языке JavaScript
Функции в JavaScript выполняют важную роль. Они обеспечивают сокращение кода за счет вынесения его в отдельные места. За урок мы научимся создавать функции и передавать в них значения.
Видеоурок
Функции можно назвать небольшими подпрограммами, куда можно вынести повторяющийся код и обращаться к нему, когда это будет нужно. Функции значительно облегчают построение программ, так как нам не надо копировать однотипный код множество раз, а можно просто воспользоваться одной общей функцией.
Многие путают функции и методы и не понимают отличий между ними. На самом деле отличий нет, так как что методы, что функции являются одним и тем же. Функции что записаны вне классов называют функциями, а функции что записаны внутри классов называются методами.
Точно такая же ситуация обстоит с переменным. В классах переменные называются полями, а вне классов — переменными.
В JS функции создаются при помощи ключевого слова function . Каждая функция может иметь какие-либо параметры или же не иметь их вовсе. Функции способны что-либо возвращать в ходе выполнения кода, если это требуется.
Создание функции
На основе всех данных наша функция будет выглядеть следующим образом:
function test()
Функция выше не принимает никаких параметров и ничего не возвращает. Она просто пишет слово в консоль. Давайте разнообразим функцию и добавим параметр:
function test(word)
Теперь функция принимает параметр, который будет отображен в консоли.
Если функция должна что-либо вернуть, то прописываем тип данных который будет возвращен. Для возвращения данных используем ключевое слово return :
function test(some_number)
Локальные и глобальные переменные
В JavaScript есть несколько полей видимости: локальная и глобальная. Если записать глобальную переменную, то такая переменная будем видна повсюду и с ней можно работать отовсюду в документе. Если записать локальную переменную, то такая переменная будет видна лишь в той области, где она записана.
Для создания глобальной переменной её необходимо прописать вне функции, класса или же объекта. Для создания локальных переменных вам достаточно поместить переменную в функцию. Переменная в функции будет видна лишь внутри блока с функцией и нигде более.
Весь код будет доступен после подписки на проект!
JavaScript Функции
JavaScript функция — это блок кода, предназначенный для выполнения определенной задачи.
JavaScript функция выполняется, когда ее вызывают (вызвает) «что-то».
Пример
function myFunction(p1, p2) <
return p1 * p2; // Функция возвращает произведение p1 и p2
>
JavaScript Синтаксис функции
JavaScript функция определяется с помощью ключевого кода function , за которым следует имя и скобки ().
Имена функций могут содержать буквы, цифры, подчеркивания и знаки доллара (те же правила, что и для переменных).
Скобки могут включать имена параметров, разделенные запятыми:
(parameter1, parameter2, . )
Код, который будет выполнен функцией, помещается в фигурные скобки: <>
function name(parameter1, parameter2, parameter3) // код для выполнения
>
Параметры функции перечислены в скобках () в определении функции.
Аргументы функции — это значения , получаемые функцией при ее вызове.
Внутри функции аргументы (параметры) действуют как локальные переменные.
Функция во многом похожа на процедуру или подпрограмму на других языках программирования.
JavaScript Вызов функции
Код внутри функции будет выполняться, когда «что-то» вызывает (вызывается) функцию:
- Когда происходит событие (когда пользователь нажимает кнопку)
- Когда он вызывает (вызывается) из JavaScript кода
- Автоматически (вызывается самостоятельно)
Вы узнаете гораздо больше о вызове функций позже в этом руководстве.
JavaScript Возврат функции
Когда, JavaScript достигает оператора return , функция прекращает выполнение.
Если функция была вызвана оператором, JavaScript «вернет» выполнение кода после вызова оператора.
Функции всегда вычисляют возвращаемое значение. Возвращаемое значение «возвращается» обратно «вызывающему»:
Пример
Вычислите произведение двух чисел и верните результат:
var x = myFunction(4, 3); // Функция вызывается, возвращаемое значение будет в конечном итоге в x
function myFunction(a, b) return a * b; // Функция возвращает произведение a и b
>
Результат в x будет:
Почему функции?
Вы можете повторно использовать код: определить код один раз и использовать его несколько раз.
Вы можете использовать один и тот же код много раз, с разными аргументами для получения разных результатов.
Пример
Преобразовать Фаренгейты в Цельсия:
function toCelsius(fahrenheit) <
return (5/9) * (fahrenheit-32);
>
document.getElementById(«demo»).innerHTML = toCelsius(77);
Оператор () вызывает функцию
В приведенном выше примере toCelsius ссылка на объект функции и toCelsius() ссылка на результат функции.
Доступ к функции без () вернет объект функции вместо результата функции.
Пример
function toCelsius(fahrenheit) <
return (5/9) * (fahrenheit-32);
>
document.getElementById(«demo»).innerHTML = toCelsius;
Функции, используемые как значения переменных
Функции можно использовать так же, как и переменные, во всех типах формул, назначений и вычислений.
Пример
Вместо использования переменной для хранения возвращаемого значения функции:
var x = toCelsius(77);
var text = «Температура » + x + » по цельсию»;
Вы можете использовать функцию напрямую, как значение переменной:
var text = «Температура » + toCelsius(77) + » по цельсию»;
Позже в этом руководстве вы узнаете гораздо больше о функциях.
Локальные переменные
Переменные, объявленные в JavaScript функции, становятся ЛОКАЛЬНЫМИ для функции.
Доступ к локальным переменным возможен только из функции.
Пример
// код здесь, нельзя использовать carName
function myFunction() var carName = «Вольво»;
// код здесь, можно использовать carName
>
// код здесь, нельзя использовать carName
Поскольку локальные переменные распознаются только внутри своих функций, переменные с одинаковыми именами могут использоваться в разных функциях.
Локальные переменные создаются при запуске функции и удаляются, когда функция завершается.
Мы только что запустили
SchoolsW3 видео
ВЫБОР ЦВЕТА
курс сегодня!
Сообщить об ошибке
Если вы хотите сообщить об ошибке или внести предложение, не стесняйтесь отправлять на электронное письмо:
Ваше предложение:
Спасибо Вам за то, что помогаете!
Ваше сообщение было отправлено в SchoolsW3.
ТОП Учебники
ТОП Справочники
ТОП Примеры
Получить сертификат
SchoolsW3 оптимизирован для бесплатного обучения, проверки и подготовки знаний. Примеры в редакторе упрощают и улучшают чтение и базовое понимание. Учебники, ссылки, примеры постоянно пересматриваются, чтобы избежать ошибок, но не возможно гарантировать полную правильность всего содержания. Некоторые страницы сайта могут быть не переведены на РУССКИЙ язык, можно отправить страницу как ошибку, так же можете самостоятельно заняться переводом. Используя данный сайт, вы соглашаетесь прочитать и принять Условия к использованию, Cookies и политика конфиденциальности.
Функции
— это блок программного кода на языке JavaScript, который определяется один раз и может выполняться, или вызываться, многократно. Возможно, вы уже знакомы с понятием «функция» под другим названием, таким как подпрограмма, или процедура. Функции могут иметь параметры: определение функции может включать список идентификаторов, которые называются параметрами и играют роль локальных переменных в теле функции.
При вызове функций им могут передаваться значения, или аргументы, соответствующие их параметрам. Функции часто используют свои аргументы для вычисления возвращаемого значения, которое является значением выражения вызова функции. В дополнение к аргументам при вызове любой функции ей передается еще одно значение, определяющее контекст вызова — значение в ключевом слове this.
Функции в языке JavaScript являются объектами и могут использоваться разными способами. Например, функции могут присваиваться переменным и передаваться другим функциям. Поскольку функции являются объектами, имеется возможность присваивать значения их свойствам и даже вызывать их методы.
В JavaScript допускается создавать определения функций, вложенные в другие функции, и такие функции будут иметь доступ ко всем переменным, присутствующим в области видимости определения.
Определение функций
Определение функции начинается с ключевого слова function, за которым указываются следующие компоненты:
Идентификатор, определяющий имя функции
Имя является обязательной частью инструкции объявления функции: оно будет использовано для создания новой переменной, которой будет присвоен объект новой функции. В выражениях определения функций имя может отсутствовать: при его наличии имя будет ссылаться на объект функции только в теле самой функции.
Пара круглых скобок вокруг списка из нуля или более идентификаторов, разделенных запятыми
Эти идентификаторы будут определять имена параметров функции и в теле функции могут использоваться как локальные переменные.
Пара фигурных скобок с нулем или более инструкций JavaScript внутри
Эти инструкции составляют тело функции: они выполняются при каждом вызове функции.
В следующем примере показано несколько определений функций в виде инструкций и выражений. Обратите внимание, что определения функций в виде выражений удобно использовать, только если они являются частью более крупных выражений, таких как присваивание или вызов функции, которые выполняют некоторые действия с помощью вновь объявленной функции:
// Выводит имена и значения всех свойств объекта obj function printprops(obj) < for(var p in obj) console.log(p + ": " + obj[p] + "\n"); >// Вычисляет расстояние между точками (x1,y1) и (x2,y2) function distance(x1, y1, x2, y2) < var dx = x2 - x1; var dy = y2 - y1; return Math.sqrt(dx*dx + dy*dy); >// Рекурсивная функция (вызывающая сама себя), вычисляющая факториал function factorial(x) < if (x // Следующее выражение определяет функцию, вычисляющую // квадрат аргумента. Обратите внимание, // что она присваивается переменной var square = function(x) < return x*x; >// Выражения определения функций могут иметь имена, что позволяет // производить рекурсивные вызовы var f = function fact(x) < if (x ; // Выражения определения функций иногда могут тут же вызываться: var tensquared = (function(x) (10));
Обратите внимание, что в выражениях определения функций имя функции может отсутствовать. Инструкция объявления функции фактически объявляет переменную и присваивает ей объект функции.
Выражение определения функции, напротив, не объявляет переменную. Однако в выражениях определения допускается указывать имя функции, как в функции вычисления факториала выше, которое может потребоваться в теле функции для вызова себя самой. Если выражение определения функции включает имя, данное имя будет ссылаться на объект функции в области видимости этой функции. Фактически имя функции становится локальной переменной, доступной только в теле функции. В большинстве случаев имя функции не требуется указывать в выражениях определения, что делает определения более компактными.
Обратите внимание, что большинство (но не все) функций в примере содержат инструкцию return. Инструкция return завершает выполнение функции и выполняет возврат значения своего выражения (если указано) вызывающей программе. Если выражение в инструкции return отсутствует, она возвращает значение undefined. Если инструкция return отсутствует в функции, интерпретатор просто выполнит все инструкции в теле функции и вернет вызывающей программе значение undefined.
Большинство функций в примере вычисляют некоторое значение, и в них инструкция return используется для возврата этого значения вызывающей программе. Функция printprops() несколько отличается в этом смысле: ее работа заключается в том, чтобы вывести имена свойств объекта. Ей не нужно возвращать какое-либо значение, поэтому в функции отсутствует инструкция return. Функция printprops() всегда будет возвращать значение undefined. (Функции, не имеющие возвращаемого значения, иногда называются процедурами.)
Вызов функций
Программный код, образующий тело функции, выполняется не в момент определения функции, а в момент ее вызова. Вызов функций выполняется с помощью выражения вызова. Выражение вызова состоит из выражения обращения к функции, которое возвращает объект функции, и следующими за ним круглыми скобками со списком из нуля или более выражений-аргументов, разделенных запятыми, внутри.
Если выражение обращения к функции является выражением обращения к свойству - если функция является свойством объекта или элементом массива (т.е. методом) - тогда выражение вызова является выражением вызова метода. В следующем фрагменте демонстрируется несколько примеров выражений вызова обычных функций:
printprops(); var d = distance(1,1,5,6); var f = factorial(5) / factorial(12); f = square(5);
При вызове функции вычисляются все выражения-аргументы (указанные между скобками), и полученные значения используются в качестве аргументов функции. Эти значения присваиваются параметрам, имена которых перечислены в определении функции. В теле функции выражения обращений к параметрам возвращают значения соответствующих аргументов.
При вызове обычной функции возвращаемое функцией значение становится значением выражения вызова. Если возврат из функции происходит по достижении ее конца интерпретатором, возвращается значение undefined. Если возврат из функции происходит в результате выполнения инструкции return, возвращается значение выражения, следующего за инструкцией return, или undefined, если инструкция return не имеет выражения.
Метод - это не что иное, как функция, которая хранится в виде свойства объекта. Если имеется функция func и объект obj, то можно определить метод объекта obj с именем method, как показано ниже:
// Определим простой объект и функцию var obj = <>; function func(a, b) < return a+b;>// Добавим в объект obj метод obj.method = func; // Теперь можно вызвать этот метод var result = obj.method(4, 5);
Чаще всего при вызове методов используется форма обращения к свойствам с помощью оператора точки, однако точно так же можно использовать форму обращения к свойствам с помощью квадратных скобок. Например, оба следующих выражения являются выражениями вызова методов:
result = obj.method(4, 5); result = obj['method'](4, 5);
Аргументы и возвращаемое значение при вызове метода обрабатываются точно так же, как при вызове обычной функции. Однако вызов метода имеет одно важное отличие: контекст вызова. Выражение обращения к свойству состоит из двух частей: объекта (в данном случае obj) и имени свойства (method). В подобных выражениях вызова методов объект obj становится контекстом вызова, и тело функции получает возможность ссылаться на этот объект с помощью ключевого слова this. Например:
var obj = < x: 0, y: 0, // Метод add: function(a, b) < this.x = a; this.y = b; >, // Еще один метод sum: function() < return this.x + this.y >>; // Вызов методов obj.add(15, 4); console.log(obj.sum()); // 19
Методы и ключевое слово this занимают центральное место в парадигме объектно-ориентированного программирования. Любая функция, используемая как метод, фактически получает неявный аргумент - объект, относительно которого она была вызвана. Как правило, методы выполняют некоторые действия с объектом, и синтаксис вызова метода наглядно отражает тот факт, что функция оперирует объектом.
Обратите внимание: this - это именно ключевое слово, а не имя переменной или свойства. Синтаксис JavaScript не допускает возможность присваивания значений элементу this.
Аргументы и параметры функций
В языке JavaScript, в определениях функций не указываются типы параметров, а при вызове функций не выполняется никаких проверок типов передаваемых значений аргументов. Фактически при вызове функций в языке JavaScript не проверяется даже количество аргументов. В подразделах ниже описывается, что происходит, если число аргументов в вызове функции меньше или больше числа объявленных параметров. В них также демонстрируется, как можно явно проверить типы аргументов функции, если необходимо гарантировать, что функция не будет вызвана с некорректными аргументами.
Необязательные аргументы
Когда число аргументов в вызове функции меньше числа объявленных параметров, недостающие аргументы получают значение undefined. Часто бывает удобным писать функции так, чтобы некоторые аргументы были необязательными и могли опускаться при вызове функции. В этом случае желательно предусмотреть возможность присваивания достаточно разумных значений по умолчанию параметрам, которые могут быть опущены. Например:
// Добавить в массив arr перечислимые имена // свойств объекта obj и вернуть его. Если аргумент // arr не не был передан, создать и вернуть новый массив function getPropertyNames(obj, /* необязательный */ arr) < if (arr === undefined) arr = []; // Если массив не определен, создать новый for(var property in obj) arr.push(property); return arr; >// Эта функция может вызываться с 1 или 2 аргументами: var a = getPropertyNames(); // Получить свойства объекта в новом массиве getPropertyNames(,a); // добавить свойства нового объекта в этот массив console.log(a); // ['x', 'y', 'z']
Обратите внимание, что при объявлении функций необязательные аргументы должны завершать список аргументов, чтобы их можно было опустить. Программист, который будет писать обращение к вашей функции, не сможет передать второй аргумент и при этом опустить первый: он будет вынужден явно передать в первом аргументе значение undefined. Обратите также внимание на комментарий /* необязательный */ в определении функции, который подчеркивает тот факт, что параметр является необязательным.
Списки аргументов переменной длины
Если число аргументов в вызове функции превышает число имен параметров, функция лишается возможности напрямую обращаться к неименованным значениям. Решение этой проблемы предоставляет объект Arguments. В теле функции идентификатор arguments ссылается на объект Arguments, присутствующий в вызове. Объект Arguments - это объект, подобный массиву, позволяющий извлекать переданные функции значения по их номерам, а не по именам.
Предположим, что была определена функция func, которая требует один аргумент x. Если вызвать эту функцию с двумя аргументами, то первый будет доступен внутри функции по имени параметра x или как arguments[0]. Второй аргумент будет доступен только как arguments[1]. Кроме того, подобно настоящим массивам, arguments имеет свойство length, определяющее количество содержащихся элементов. То есть в теле функции func, вызываемой с двумя аргументами, arguments.length имеет значение 2.
Объект Arguments может использоваться с самыми разными целями. Следующий пример показывает, как с его помощью проверить, была ли функция вызвана с правильным числом аргументов, - ведь JavaScript этого за вас не сделает:
function func(x, y, z) < // Сначала проверяется, правильное ли количество аргументов передано if (arguments.length != 3) < throw new Error("Функция func вызвана с " + arguments.length + " аргументами, а требуется 3."); >// А теперь сам код функции. >
Обратите внимание, что зачастую нет необходимости проверять количество аргументов, как в данном примере. Поведение по умолчанию интерпретатора JavaScript отлично подходит для большинства случаев: отсутствующие аргументы замещаются значением undefined, а лишние аргументы просто игнорируются.
Объект Arguments иллюстрирует важную возможность JavaScript-функций: они могут быть написаны таким образом, чтобы работать с любым количеством аргументов. Следующая функция принимает любое число аргументов и возвращает значение самого большого из них (аналогично ведет себя встроенная функция Math.max()):
function maxNumber() < var m = Number.NEGATIVE_INFINITY; // Цикл по всем аргументам, поиск и // сохранение наибольшего из них for(var i = 0; i < arguments.length; i++) if (arguments[i] >m) m = arguments[i]; // Вернуть наибольшее значение return m; > var largest = maxNumber(1, 10, 100, 2, 3, 1000, 4, 5, 10000, 6); // 10000
Функции, подобные этой и способные принимать произвольное число аргументов, называются . Этот термин возник вместе с появлением языка программирования C.
Обратите внимание, что функции с переменным числом аргументов не должны допускать возможность вызова с пустым списком аргументов. Будет вполне разумным использовать объект arguments[] при написании функции, ожидающей получить фиксированное число обязательных именованных аргументов, за которыми может следовать произвольное число необязательных неименованных аргументов.
Не следует забывать, что arguments фактически не является массивом - это объект Arguments. В каждом объекте Arguments имеются пронумерованные элементы массива и свойство length, но с технической точки зрения это не массив. Лучше рассматривать его как объект, имеющий некоторые пронумерованные свойства.
Помимо элементов своего массива объект Arguments определяет свойства callee и caller. При попытке изменить значения этих свойств в строгом режиме ECMAScript 5 гарантированно возбуждается исключение TypeError. Однако в нестрогом режиме стандарт ECMAScript утверждает, что свойство callee ссылается на выполняемую в данный момент функцию. Свойство caller не является стандартным, но оно присутствует во многих реализациях и ссылается на функцию, вызвавшую текущую.
Свойство caller можно использовать для доступа к стеку вызовов, а свойство callee особенно удобно использовать для рекурсивного вызова неименованных функций:
var factorial = function(x) < if (x ;
Свойства и методы функций
Мы видели, что в JavaScript-программах функции могут использоваться как значения. Оператор typeof возвращает для функций строку «function», однако в действительности функции в языке JavaScript - это особого рода объекты. А раз функции являются объектами, то они имеют свойства и методы, как любые другие объекты. Существует даже конструктор Function(), который создает новые объекты функций. В следующих подразделах описываются свойства и методы функций.
Свойство length
В теле функции свойство arguments.length определяет количество аргументов, переданных функции. Однако свойство length самой функции имеет иной смысл. Это свойство, доступное только для чтения, возвращает количество аргументов, которое функция ожидает получить - число объявленных параметров.
В следующем фрагменте определяется функция с именем check(), получающая массив аргументов arguments от другой функции. Она сравнивает свойство arguments.length (число фактически переданных аргументов) со свойством arguments.callee.length (число ожидаемых аргументов), чтобы определить, передано ли функции столько аргументов, сколько она ожидает. Если значения не совпадают, генерируется исключение. За функцией check() следует тестовая функция func(), демонстрирующая порядок использования функции check():
// Эта функция использует arguments.callee, поэтому она // не будет работать в строгом режиме function check(args) < var actual = args.length; // Фактическое число аргументов var expected = args.callee.length; // Ожидаемое число аргументов if (actual !== expected) // Если не совпадают, генерируется исключение throw new Error("ожидается: " + expected + "; получено " + actual); >function func(x, y, z) < // Проверить число ожидаемых и фактически переданных аргументов check(arguments); // Теперь выполнить оставшуюся часть функции return x + y + z; >
Свойство prototype
Любая функция имеет свойство prototype, ссылающееся на объект, известный как объект прототипа. Каждая функция имеет свой объект прототипа. Когда функция используется в роли конструктора, вновь созданный объект наследует свойства этого объекта прототипа.
Прототипы и свойство prototype обсуждались в предыдущей статье.
Методы call() и apply()
Методы call() и apply() позволяют выполнять косвенный вызов функции, как если бы она была методом некоторого другого объекта. Первым аргументом обоим методам, call() и apply(), передается объект, относительно которого вызывается функция; этот аргумент определяет контекст вызова и становится значением ключевого слова this в теле функции. Чтобы вызвать функцию func() (без аргументов) как метод объекта obj, можно использовать любым из методов, call() или apply():
func.call(obj); func.apply(obj);
Любой из этих способов вызова эквивалентен следующему фрагменту (где предполагается, что объект obj не имеет свойства с именем m):
obj.m = func; // Временно сделать func методом obj obj.m(); // Вызывать его без аргументов. delete obj.m; // Удалить временный метод.
В строгом режиме ECMAScript 5 первый аргумент методов call() и apply() становится значением this, даже если это простое значение, null или undefined. В ECMAScript 3 и в нестрогом режиме значения null и undefined замещаются глобальным объектом, а простое значение - соответствующим объектом-оберткой.
Все остальные аргументы метода call(), следующие за первым аргументом, определяющим контекст вызова, передаются вызываемой функции. Метод apply() действует подобно методу call(), за исключением того, что аргументы для функции передаются в виде массива. Если функция способна обрабатывать произвольное число аргументов, метод apply() может использоваться для вызова такой функции в контексте массива произвольной длины.
В следующем примере демонстрируется практическое применение метода call():
// Ниже определены две функции, отображающие свойства и // значения свойств произвольного объекта. Способ // отображения передаются в виде аргумента func function print1(func, obj) < for (n in obj) func(n +': ' + obj[n]); >function print2(func, objDevice, obj) < for (n in obj) func.call(objDevice, n +': ' + obj[n]); >var obj = ; print2(document.write, document, obj); // Работает корректно print2(console.log, console, obj); print1(document.write, obj); // Возникнет исключение Illegal invocation, т.к. print1(console.log, obj); // невозможно вызвать эти методы без объекта контекста
Метод bind()
Метод bind() впервые появился в ECMAScript 5, но его легко имитировать в ECMAScript 3. Как следует из его имени, основное назначение метода bind() состоит в том, чтобы связать (bind) функцию с объектом. Если вызвать метод bind() функции func и передать ему объект obj, он вернет новую функцию. Вызов новой функции (как обычной функции) выполнит вызов оригинальной функции func как метода объекта obj. Любые аргументы, переданные новой функции, будут переданы оригинальной функции. Например:
// Функция, которую требуется привязать function func(y) < return this.x + y; >var obj = ; // Объект, к которому выполняется привязка var g = func.bind(obj); // Вызов g(x) вызовет obj.func(x)
Такой способ связывания легко реализовать в ECMAScript 3, как показано ниже:
// Возвращает функцию, которая вызывает func как метод объекта obj // и передает ей все свои аргументы function bind(func, obj) < if (func.bind) return func.bind(obj); // Использовать метод bind, если имеется else return function() < // Иначе связать, как показано ниже return func.apply(obj, arguments); >; >
Метод bind() в ECMAScript 5 не просто связывает функцию с объектом. Он также выполняет частичное применение: помимо значения this связаны будут все аргументы, переданные методу bind() после первого его аргумента. Частичное применение - распространенный прием в функциональном программировании и иногда называется каррингом (currying).