2017-01-28 23 views
1

我正在学习Angular2,关于Angular.io的“Tour of Heroes”教程。在教程结尾附近,我们设置了路由到详细信息页面并传递了一个参数,指示要替换的英雄。这是使用ActivatedRoute中的参数Observable处理的。我们使用switchMap将参数Observable重定向到Promise,以根据参数返回我们实际需要的数据。使用带有Promises的switchMap

本教程中使用的语法是简洁的,所以我试图将其分解为构建块以更好地理解正在发生的事情。具体来说,我试图用实际的功能替换右箭头符号,我认为它是相同的。但我的修改不起作用。

下面是代码:

ngOnInit(): void { 
     this.route.params 
     .switchMap((params: Params) => this.heroService.getHero(+params['id'])) 
     //.switchMap(this.getHero) 
     .subscribe(hero => this.hero = hero); 
    } 

    getHero(params: Params) : Promise<Hero> { 
     return this.heroService.getHero(+params['id']); 
    } 

什么让我困惑的是,为什么使用目前注释掉,而不是它上面的线的线,我得到一个错误:"Cannot read property 'getHero' of undefined."代码的两个版本看上去相同我。

+1

其中之一是一个方法,其他与绑定'this'箭头功能。你确定它在'.getHero'错误,而不是函数内部的'.heroService'? – Bergi

+0

[如何在回调中访问正确的\'this \'](https://stackoverflow.com/questions/20279484/how-to-access-the-correct-this-inside-a-callback) ) – echonax

回答

1

胖箭头功能保留执行上下文,允许this“变量”与父范围中的相同。如果您使用.switchMap(this.getHero),则this将指向其他内容,而不是组件。

getHero(params: Params) : Promise<Hero> { 
    // "this" is not what you expect here 
    return this.heroService.getHero(+params['id']); 
} 

所以this.heroService在此处未定义。

0

程式码中不能使用this.getHero喜欢,因为

  1. undefined(服务返回Observable,你必须subscribe使用其数据前)
  2. 它不是一个属性(没有get modifyer )。
1

你需要bind你的getHero函数。

.switchMap(this.getHero.bind(this)) 

否则您的更改是相同的。像这样使用绑定可以让您将getHero作为独立函数传递给switchMap,而不会丢失this对其的意义。

你可以自己做个实验:

'use strict'; 
const foo = { 
    bar: 'baz', 
    getBar: function() { 
    return this.bar; 
    } 
}; 

foo.getBar(); 
// => 'baz' 

const myGetBar = foo.getBar; 
myGetBar(); 
// => TypeError: Cannot read property 'bar' of undefined 

const boundGetBar = foo.getBar.bind(foo); 
boundGetBar(); 
// => 'baz' 

const otherObj = { bar: 'hi' }; 
const otherBoundGetBar = foo.getBar.bind(otherObj); 
otherboundGetBar(); 
// => 'hi' 

otherObj.getBar = myGetBar; 
otherObj.getBar(); 
// => 'hi'