تابعی که "this" را از دست میدهد را تصحیح کنید
فراخوانی askPassword()
در کد پایین باید رمز یا چک کند و سپس با توجه به جواب user.loginOk/loginFail
را فراخوانی کند.
اما به ارور برمیخورد. چرا؟
خط برجسته شده را تصحیح کند تا همه چیز به درستی کار کند (بقیه خطوط نیازی به تغییر ندارند).
function askPassword(ok, fail) {
let password = prompt("رمز؟", '');
if (password == "rockstar") ok();
else fail();
}
let user = {
name: 'John',
loginOk() {
alert(`${this.name} وارد شد`);
},
loginFail() {
alert(`${this.name} نتوانست وارد شود`);
},
};
askPassword(user.loginOk, user.loginFail);
به دلیل اینکه ask
تابعهای loginOk/loginFail
را بدون شیء دریافت میکند ارور ایجاد میشود.
زمانی که این تابع آنها را فرا میخواند، به طور طبیعی آنها this=undefined
را فرض میکنند.
بیایید زمینه را با bind
پیوند بزنیم:
function askPassword(ok, fail) {
let password = prompt("رمز؟", '');
if (password == "rockstar") ok();
else fail();
}
let user = {
name: 'John',
loginOk() {
alert(`${this.name} وارد شد`);
},
loginFail() {
alert(`${this.name} نتوانست وارد شود`);
},
};
askPassword(user.loginOk.bind(user), user.loginFail.bind(user));
حالا کار میکند.
راهحل جایگزین میتواند این باشد:
//...
askPassword(() => user.loginOk(), () => user.loginFail());
معمولا این راهحل هم کار میکند و ظاهر خوبی دارد.
اگرچه این کد در موقعیتهای پیچیدهتر کمتر قابل اطمینان است، زمانی که متغیر user
ممکن است بعد از اینکه askPassword
فراخوانی شود و قبل از اینکه کاربر جواب بدهد و () => user.loginOk()
را فرا بخواند، تغییر کند.