0
votes

I have view model in which I have an observable array. I have a computed observable which is calculated once the observable array is populated I am looping through the items of the array and computing the computed observable.

This computed observable is referenced in some other computed observables. So each time this computed observable is referenced the looping is done once again. Can any any one suggest how we can avoid this. So that the computed observable executes the looping only once.

1
Show some code. Otherwise impossible to guess what is happening. In general, a computed observable shouldn't be recalculated unless one of the observables it depends on is modified. - Matt Burland
Please share your code. I suspect rateLimit is what you're looking for. - TrueEddie

1 Answers

0
votes

Depending on how you have declared your computed observable (I'm assuming the typical ko.computed(evaluator), then every time you read that computed the evaluator will execute to evaluate it.

Considering you have stated "This computed observable is referenced in some other computed observables", every one of those references is performing a read.

In general, you need to "cache" the result of your processing.

The easiest way to prevent the duplicate processing is to not use the computed directly in a dependency chain. Instead, within the evaluator you'd modify some other observable property of your viewmodel and establish dependencies on that observable.

var vm = {data: ko.observableArray(), obs: ko.observable()}
vm.modifiesModelProperty = ko.computed(function(){
  vm.obs("Some Evaluated Expression for " + vm.data())
})
vm.anotherComputed = ko.computed(function(){
  return vm.obs();
})

If you are insistent on using the computed and wanted to encapsulate the caching within it.

vm.computed = ko.computed({

  owner: (function(){
          var self = this;
          self.cachingObservable = ko.observable()

          vm.data.subscribe(function(nv){ 
              self.cachingObservable("Some Evaluated Expression for " + nv)
          });
  })(),
  read: this.cachingObservable,
})

You could use a combination of both approaches and set owner to be your viewmodel and modify some observable property that way. In this case, read would return that observable.