Как работает метод `bind()` и почему при замене оригинальной функции в объекте на другую все еще вызывается исходная функция?
Метод `bind()` в JavaScript используется для создания новой функции, у которой указан контекст выполнения (this) и набор параметров заданы заранее.
Принцип работы метода `bind()` прост: он создает новую функцию, которая будет вызывать исходную функцию, но с жестко привязанным контекстом выполнения и, при необходимости, частью аргументов.
Когда вы вызываете `bind()` для оригинальной функции в объекте и присваиваете эту новую функцию обратно в объект, то исходная функция все еще вызывается, потому что вы создали копию этой функции с новым контекстом, но не перезаписали оригинальную функцию в объекте. Таким образом, при вызове метода через объект, вызывается оригинальная функция, а не новая, созданная с помощью `bind()`.
Для того чтобы перезаписать оригинальную функцию в объекте новой функцией с привязанным контекстом, можно просто переприсвоить свойство объекта на результат вызова `bind()`.
Пример:
```javascript
const obj = {
name: 'Alice',
sayHello: function() {
console.log('Hello, ' + this.name);
}
};
const newFunc = obj.sayHello.bind({ name: 'Bob' });
obj.sayHello = newFunc; // перезаписываем оригинальную функцию
obj.sayHello(); // выведет: "Hello, Bob"
```
<code>bind</code> кэширует текущее значение своего <code>this</code> в момент своего вызова, т.е. он привязывает именно функцию, а не объект, в котором находится функция. Иначе нельзя было бы вызывать bind на просто функции по типу <code>foo.bind(abc)</code> . В мануале, кстати, описано что именно она кэширует - там полный список есть: <a href="https://developer.mozilla.org/ru/docs/Web/JavaScript/Reference/Global_Objects/Function/bind" rel="nofollow">https://developer.mozilla.org/ru/docs/Web/JavaScri...</a> <br/> <br/> Упрощенный пример реализации <code>bind</code> для понимания механизма: <br/> <pre><code class="javascript">function binder(that) {
let targetFunction = this; // кэш целевой функции
return function() { targetFunction.call(that) } // В возвращаемой функции используем кэш
}
let user = {
name: "Tom",
intro() {
console.log("I am " + this.name);
}
}
user.intro.binder = binder
let f = user.intro.binder(user);
setTimeout(f, 1000);
user.name = "Sid";
user.intro = function() {
console.log("Вообще другая функция. name: " + this.name);
}</code></pre>