> For the complete documentation index, see [llms.txt](https://strctr.gitbook.io/programming/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://strctr.gitbook.io/programming/01-languages/javascript/01-language/c-functions/c1-functions/03.ii-bound-function.md).

# 03.ii Bound Function

A **bound function** is a function bind with an object using `fn.bind(obj)` method. As a result of bind call we receive new function with a `this` bound to `obj` forever. `.bind()` makes a permanent context link and will always keep it.&#x20;

The original and bound functions share the same code and scope, but different contexts on execution. `this` is the first argument of `.bind()` when invoking a bound function.

`fun.bind(thisArg, [arg1, arg2, ...])`

* `thisArg` value to be passed as the this parameter to the target function when the bound function is called. The value is ignored if the bound function is constructed using the `new` operator.
* `[arg1, arg2, ...]` - arguments provided to the bound function when invoking the target function.

In general, `.bind` function is equals to following code:

```javascript
function bind(func, context) {
  return function() {
    return func.apply(context, arguments);
  };
}
```

Методы `call`/`apply` вызывают функцию с заданным контекстом и аргументами. А `bind` не вызывает функцию. Он только возвращает «обёртку», которую мы можем вызвать позже, и которая передаст вызов в исходную функцию, с привязанным контекстом.

## Use `bind` to carry function:

> **Карринг** (currying) или каррирование – термин функционального программирования, который означает создание новой функции путём фиксирования аргументов существующей.

При помощи `bind` удобно выполнять каррирование функции:

```javascript
function mul(a, b) {
  return a * b;
}
// double умножает только на два
var double = mul.bind(null, 2); // контекст фиксируем null, он не используется

double(3); // = mul(2, 3) = 6
double(4); // = mul(2, 4) = 8
double(5); // = mul(2, 5) = 10
```

Говорят, что `double` является *частичной функцией* (partial function) от `mul`.

## Decorate functions with `bind`

Через функцию `bind` и привязку контекста очень удобно делать функции-декораторы поверх других функций. Создадим декоратор, замеряющий время выполнения функции. Он будет называться `timingDecorator` и получать функцию вместе с «названием таймера», а возвращать — функцию-обёртку, которая измеряет время и прибавляет его в специальный объект `timer` по свойству-названию:

```javascript
const timers = {};

// прибавит время выполнения f к таймеру timers[timer]
function timingDecorator(f, timer) {
  return function() {
    const start = performance.now();

    const result = f.apply(this, arguments); // (*)

    if (!timers[timer]) timers[timer] = 0;
    timers[timer] += performance.now() - start;

    return result;
  };
}

// функция может быть произвольной, например такой:
function fibonacci(n) {
  return n > 2 ? fibonacci(n - 1) + fibonacci(n - 2) : 1;
}

// использование: завернём fibonacci в декоратор
fibonacci = timingDecorator(fibonacci, "fibo");

// неоднократные вызовы...
fibonacci(10); // 55
fibonacci(20); // 6765
// ...

// в любой момент можно получить общее количество времени на вызовы
alert(timers.fibo + "мс");
```

Декораторы можно не только повторно использовать, но и комбинировать!

Это кардинально повышает их выразительную силу. Декораторы можно рассматривать как своего рода возможности, которые можно «нацепить» на любую функцию. Можно один, а можно несколько.
