Angular2 Observable обновляет частную переменную

Не уверен, правильно ли я задаю вопрос, но у меня есть служба, которая используется для совместного использования объекта массива между различными компонентами. Однако, когда я отправляю новый объект в службу, что-то обновляет все другие объекты в моем массиве службы.

т.е. ответы первого нажатия = [{questionId: 1, значение: 1}] второе нажатие с ответами {questionId: 1, значение: 3} = [{questionId: 1, значение: 3}, {questionId: 1, значение: 3} ]

Обратите внимание, как значение изменяется, чтобы соответствовать значению только что отправленного объекта ответа.

это мой сервис

export interface Answer {
  questionId: number;
  value: number;
}

  private answers: Answer[] = [];
  private _answers: BehaviorSubject<Answer[]> = new BehaviorSubject([]);
  public answers$ = this._answers.asObservable();


  addAnswer(answer: Answer) {
    this.answers.push(answer);
    this._answers.next(this.answers);
  }

это мой компонент

export class LevelComponent {
  subscription: Subscription;
  answer: Answer = {questionId: 0, value: 0}; 
  a: Answer[];
  constructor(public route: ActivatedRoute, public answerService: AnswerService) {

  }

  ngOnInit() {

    this.subscription = this.answerService.answers$.subscribe(item => this.a = item);


  }
  ngOnDestroy() {
    // prevent memory leak when component is destroyed
    this.subscription.unsubscribe();
  }


  submitAnswer(e){
    console.log(e.target.id);
    this.answer.questionId = 1;
    this.answer.value = e.target.id;

    this.answerService.addAnswer(this.answer);
  }

По сути, я хочу «поделиться» массивом ответов между несколькими компонентами, но ограниченное понимание BehaviorSubject и подписок вызывает недоумение относительно того, почему после добавления нового элемента в обслуживаемый массив он будет обновлять все другие объекты. Кстати, если я изменю переменную ответа просто на число, значения в массиве не изменятся, когда я отправлю ответ.

Вот Plunker, иллюстрирующий то, что я вижу.


person utd1878    schedule 08.12.2016    source источник
comment
Что вы имеете в виду под обновить все остальные объекты? Не могли бы вы привести минимально воспроизводимый пример?   -  person jonrsharpe    schedule 08.12.2016
comment
обновлен с примером того, как обновляется объект ответа   -  person utd1878    schedule 08.12.2016
comment
@jonrsharpe добавил плунжер   -  person utd1878    schedule 08.12.2016


Ответы (2)


Вероятно, потому что вы делаете это:

this.answers.push(answer);
this._answers.next(this.answers);

когда вам нужно только это сделать

this._answers.next(answer);

Т.е. вызывая next со всем массивом, ваши подписчики получат весь массив как следующий элемент, а не только следующий элемент.

person williamsandonz    schedule 08.12.2016
comment
_answers — это BehaviorSubject‹Answer[]›. answer - это только один объект ответа. Как мне вставить новый ответ в переменную _answers? - person utd1878; 08.12.2016

Спасибо тем, кто посмотрел на мой вопрос.

Итак, получается, что мой сервис был исправен и функционировал, как ожидалось. Проблема заключалась в том, что я каждый раз передавал одну и ту же ссылку своего ответа на вызов addAnswer, поэтому он обновлял указанный ответ, который, в свою очередь, обновлял каждый объект в массиве.

Исправление заключалось в том, чтобы объявлять новый ответ каждый раз перед отправкой.

  submitAnswer(e){
    let answer: Answer = {questionId: 1, value: e.target.id};
    this.answerService.addAnswer(answer);
  }
person utd1878    schedule 08.12.2016