Разница между этими двумя конструкциями кода Javascript
Я случайно наткнулся на следующий код JavaScript, и он прекрасно работает.
var Mario = {
name: 'Mario',
sayHello: function(name) {
return 'Hi I\'m ' + this.name;
}
};
var Luigi = {
name: 'xoxox'
};
alert(Mario.sayHello.call(Luigi , name));
Однако, когда я изменяю свойство name на что-то другое (скажем, xyz), вот так:
var Mario = {
xyz: 'Mario',
sayHello: function(xyz) {
return 'Hi I\'m ' + this.xyz;
}
};
var Luigi = {
xyz: 'xoxox'
};
alert(Mario.sayHello.call(Luigi , xyz));
Это не работает!!
Что означает это поведение и почему оно не работает? Может кто-нибудь объяснить?
3 ответа
Ну, технически, ваш name
пример не работает Это выполняется потому, что есть переменная name
в глобальном пространстве имен (window.name
).
Ошибка здесь:
var Mario = {
name: 'Mario',
sayHello: function(name) {
return 'Hi I\'m ' + this.name;
}
};
sayHello - это функция, которая получает имя в качестве параметра и ничего с ним не делает. Вместо этого он возвращает строку со свойством name
объекта была вызвана функция.
Mario.sayHello() // Hi I'm Mario
Mario.sayHello.call({ name: 'Foo'}) // Hi I'm Foo
Когда вы делаете Mario.sayHello(myname)
, функция sayHello вызывается в контексте Марио с name
параметр, инициализированный тем, что есть в myname (может даже быть ошибкой, если myname не существует).
Если вы хотите дать имя свойства в качестве параметра, вы можете сделать:
var Mario = {
name: 'Mario',
sayHello: function(name) {
return 'Hi I\'m ' + this[name];
}
};
var Luigi = {
xyz: 'xoxox'
};
alert(Mario.sayHello.call(Luigi , 'xyz')); // Hi I'm xoxox
Оба не работают, причина в том, что вы передаете второе, не определенное значение, вызову call
вы можете сделать
var Mario = {
name: 'Mario',
sayHello: function() {
return 'Hi I\'m ' + this.name;
}
};
var Luigi = {
name: 'xoxox'
};
alert(Mario.sayHello.call(Luigi));
Там нет необходимости проходить name
, так как это уже в объекте.