Книга: JavaScript. Подробное руководство, 6-е издание
8.7.4. Метод bind()
8.7.4. Метод bind()
Метод bind()
впервые появился в ECMAScript 5, но его легко имитировать в ЕСМА-Script 3. Как следует из его имени, основное назначение метода bind()
состоит в том, чтобы связать (bind) функцию с объектом. Если вызвать метод bind()
функции f и передать ему объект о, он вернет новую функцию. Вызов новой функции (как обычной функции) выполнит вызов оригинальной функции f как метода объекта о. Любые аргументы, переданные новой функции, будут переданы оригинальной функции. Например:
function f(у) { return this.x + у: } // Функция, которую требуется привязать
var о = { х : 1 }; // Объект, к которому выполняется привязка
var g = f.bind(o); // Вызов g(х) вызовет o.f(x)
g(2) // => 3
Такой способ связывания легко реализовать в ECMAScript 3, как показано ниже:
// Возвращает функцию, которая вызывает f как метод объекта о
// и передает ей все свои аргументы,
function bind(f, о) {
if (f.bind) return f.bind(o): // Использовать метод bind, если имеется
else return function() { // Иначе связать, как показано ниже
return f.apply(o, arguments):
};
}
Метод bind()
в ECMAScript 5 не просто связывает функцию с объектом. Он также выполняет частичное применение: помимо значения this
связаны будут все аргументы, переданные методу bind()
после первого его аргумента. Частичное применение - распространенный прием в функциональном программировании и иногда называется каррингом (currying). Ниже приводится несколько примеров использования метода bind()
для частичного применения:
var sum = function(x,у) { return х + у }; // Возвращает сумму 2 аргументов
// Создать новую функцию, подобную sum, но со связанным значением null
// ключевого слова this и со связанным значением первого аргумента, равным 1.
// Новая функция принимает всего один аргумент,
var succ = sum.bind(null, 1);
succ(2) // => 3: аргумент x связан со значением 1, а 2 передается в арг. у
function f(y.z) { return this.x + у + z }; // Еще одна функция сложения
var g = f.bind({x:1}, 2); // Связать this и у
g(3) // => 6: this.x - связан с 1, у - связан с 2, а 3 передается в z
В ECMAScript 3 также возможно связывать значение this
и выполнять частичное применение. Стандартный метод bind()
можно имитировать программным кодом, который приводится в примере 8.5. Обратите внимание, что этот метод сохраняется как Function.prototype.bind
, благодаря чему все функции наследуют его. Данный прием подробно рассматривается в разделе 9.4.
Пример 8.5. Метод Function.bind() для ECMAScript 3
if (!Function.prototype.bind) {
Function.prototype.bind = function(o /*, аргументы */) {
// Сохранить this и arguments в переменных, чтобы их можно было
// использовать во вложенной функции ниже,
var self = this, boundArgs = arguments;
// Возвращаемое значение метода bind() - функция
return function() {
// Сконструировать список аргументов, начиная со второго аргумента
// метода bind, и передать все эти аргументы указанной функции,
var args = [], і;
fог(і = 1; і < boundArgs.length; i++) args.push(boundArgs[i]);
for(i = 0; і < arguments.length; i++) args.push(arguments[i]);
// Теперь вызвать self как метод объекта о со всеми аргументами
return self.apply(о, args);
};
};
}
Обратите внимание, что функция, возвращаемая этим методом bind(),
является замыканием, использующим переменные self
и boundArgs,
объявленные во внешней функции, которые остаются доступными вложенной функции даже после того, как она будет возвращена внешней функцией и вызвана из-за пределов внешней функции.
Метод bind(),
определяемый стандартом ECMAScript 5, имеет некоторые особенности, которые невозможно реализовать в ECMAScript 3. Прежде всего, настоящий метод bind()
возвращает объект функции, свойство length
которой установлено в соответствии с количеством параметров связываемой функции, минус количество связанных аргументов (но не меньше нуля). Во-вторых, метод bind(
) в ECMAScript 5 может использоваться для частичного применения функций-конструкторов. Если функцию, возвращаемую методом bind(),
использовать как конструктор, значение this
, переданное методу bind(),
игнорируется, и оригинальная функция будет вызвана как конструктор, с уже связанными аргументами, если они были определены. Функции, возвращаемые методом bind(),
не имеют свойства prototype (свойство prototype обычных функций нельзя удалить), и объекты, созданные связанными функциями-конструкторами, наследуют свойство prototype оригинального, несвязанного конструктора. Кроме того, с точки зрения оператора instanceof
связанные конструкторы действуют точно так же, как несвязанные конструкторы.
- Data Binding Using the GridView Control
- Providing DNS for a Real Domain with BIND
- Using Fedora's BIND Configuration Tool
- 15.7.1 Назначение rpcbind
- 2.4.3. Dynamic Binding
- 10.3.3. Binding a Client to a Server
- The BIND 8 host.conf File
- Browsing and Manipulating Bindery Data
- Configuring server bindings
- Data Binding
- Главный конфигурационный файл BIND
- Запуск сервера BIND в рамках поддерева chroot