2017-01-04 12 views
0

なぜangular2は変数のすべての参照を更新していますか?angular2も参照変数の更新を避ける

問題文: 私はgetDataメソッドから返されると、いくつかのフィルタリングを行って、観察に加入することだし、それが

正常に動作しているgetDataメソッドコンポーネントで

@Injectable() 
export class BuildingService { 

constructor(private http: Http){  
    } 

buildings$: Observable<Building[]>; 

getData() : Observable<Building[]>{ 
    if (this.buildings$) { 
     this.buildings$ = this.http.get('http://localhost:8080/buildings') 
     .map(this.extractData) 
     .publishReplay(1) 
     .refCount();  
    } 
    return this.buildings$; 
    } 

private extractData(res: Response) { 
    let body = res.json(); 
    return body; 
} 
} 

呼び出しに観測可能返すサービスを持っています

export class Component1 implements onInit{ 

    constructor(private _buildingService: BuildingService) {} 

    buildings: Building[] = []; 

    ngOnInit() { 
     this._buildingService.getData() 
     .subscribe(buildings => { 
      this.buildings = buildings; 
      this.buildings.forEach((building, index){ 
       if (building.id === 0) { 
        this.buildings.splice(index, 1); 
       } 
      }); 
     });  
    } 

getUnfilteredData() { 
    this._buildingService.getData() 
     .subscribe(buildings => { 
      this.buildings = buildings;   
     }); 
    } 
} 

でも、getUnfilteredData()を呼び出しても、以前にフィルタリングされたデータが取得されています。誰かがなぜこの動作があり、これを回避する方法を説明できますか?

+0

あなたが最初の呼び出し 'ngOnInit'が、その後、this.buildings''フィルタリング。後であなたは同じサービスを呼び出し、コールバックの '建物'は 'this.buildings'ですか?あなたは 'console.log(建物);'購読者の中にいますか? – echonax

+0

@echonax getUnfilteredDataの内部にconsole.log(建物)を作成しました。私はフィルタリングされていないデータの代わりにフィルタリングされたデータを取得しています。 –

答えて

2

.publishReplay(1).refCount();を使用して、動作している複数のサブスクライバのデータをキャッシュしています。しかし、ngOninitでは元のデータ参照をthis.buildingsにしてスプライスしています。したがって、キャッシュされたデータも影響を受けます。

解決策は、フィルタリングする前にアレイをスライスしてthis.buildingsにスライス(コピーを作成)することです。

ngOnInit() { 
     this._buildingService.getData() 
     .subscribe(buildings => { 
      this.buildings = buildings.slice();//slice instead of taking reference 
      this.buildings.forEach((building, index){ 
       if (building.id === 0) { 
        this.buildings.splice(index, 1); 
       } 
      }); 
     });  
    } 

それとも、これを行うことができます:

ngOnInit() { 
      this.buildings = []; 
      this._buildingService.getData() 
      .subscribe(buildings => { 

       buildings.forEach((building){ 
        if (building.id !== 0) { 
         this.buildings.push(building); 
        } 
       }); 
      });  
     } 
+0

どうすれば建物の配列に1つ以上の配列が含まれていますか?スライスが配列内の配列で動作していないように見えます。 –

+0

更新の回答.. –

+0

購読したデータをコンポーネントアレイに簡単にフィルタリングすることができます。 –

関連する問題