Przejdź do głównej zawartości

Bug #079

🪲 Znajdź buga

const myObject = {
message: "Hello world!",
showMessage() {
setTimeout(function () {
console.log(this.message)
}, 500)
},
}

myObject.showMessage()

Chcemy zalogować do konsoli, z lekkim opóźnieniem, wiadomość powitalną zdefiniowaną we własności obiektu.

Co dokładnie zostanie zalogowane do konsoli w powyższym przykładzie?

🧪 Rozwiązanie

const myObject = {
message: "Hello world!",
showMessage() {
setTimeout(function () {
console.log(this.message)
}.bind(myObject), 500)
},
}

myObject.showMessage()

W błędnym przykładzie do konsoli zostanie zalogowana wartość undefined.

Globalna funkcja setTimeout() to tak naprawdę metoda globalnego obiektu (window lub global).

Wywołanie this wewnątrz zwrotnej funkcji (callback) przekazanej do setTimeout() skutkuje więc wskazywaniem this na obiekt globalny, który nie ma zdefiniowanej własności message.

this jest zawsze zależne od kontekstu, w którym zostaje wywołane.

Aby przypisać interesujący nas kontekst obiektu myObject możemy użyć metody bind() na anonimowej funkcji przekazywanej jako callback do setTimeout().

Innym sposobem może być zamienienie deklaracji anonimowej funkcji callback na wyrażenie funkcji strzałkowej.

Dzięki temu this będzie odnosiło się do wyższego kontekstu, ponieważ funkcje strzałkowe nie mają własnego wiązania dla this.

🎢 Plac zabaw

Otwórz edytor w nowym oknie

📑 Linki

❤️ Podobają Ci się bugi JS?

Podziel się linkiem ze znajomymi:
https://codisity.pl/100-bugow-js