Skip navigation.
 
mlRe: KVO and the observeValueForKeyPath bottleneck
FROM : George Orthwein
DATE : Thu Jul 20 21:25:20 2006

On Jul 18, 2006, at 8:44 PM, Matt Neuburg wrote:
> Interestingly, though (or perhaps not, for those who already 
> realized this),
> if what you are planning to do when you get notified thru 
> observeValue... is
> set a corresponding ivar, it might be much simpler to avoid the entire
> problem and use bind:... instead of addObserver:... at the outset.


Thanks for this idea, though I actually arrived at my current 
observeValueForKeyPath: implementation because I had initially using 
bindings! :)
http://www.cocoabuilder.com/archive/message/cocoa/2006/4/17/161225

I already had all the setters there that were called with 
bind:toObject:withKeyPath:options: so when I switched to KVO, it 
naturally led into trying to call them from my 
observeValueForKeyPath: method.

One nice thing is that I can switch back and forth easily just by 
swapping out:
[sender bind:@"attributeName" toObject:docPrefsController 
withKeyPath:@"selection.attributeName" options:nil];
for
[docPrefsController addObserver:sender 
forKeyPath:@"selection.attributeName" options:nil context:NULL];
As you point out, one passes through observeValueForKeyPath: and one 
calls the accessors directly.

The main reason I switched away from using bind: was that I found my 
setters getting called something like a dozen times when the binding 
was first initiated with bind:toObject:withKeyPath:options:. Perhaps 
there's a way to coalesce those initial updates. I found it was 
bogging down the initial display of the view since it triggered a 
dozen or so redraws.
(Ok, I just double checked this and I'm only seeing a single initial 
call now when I use bind:! Not sure what I was seeing before because 
in my notes I even mention some accessors getting called 24 times! I 
probably setup something wrong at some point, though I thought I had 
also seen this mentioned in the archives somewhere. More 
investigation is in order....)

One thing that tripped me up when I switched to KVO is that 
addObserver:forKeyPath:options:context: does NOT send the current 
value on initial registration. This means that to sync the view 
initially I have to enumerate through the relevant attributes and 
call setValue:forKey: manually.
http://www.cocoabuilder.com/archive/message/cocoa/2006/5/20/163920

> The point there was that if I say bind:..., I get a "one-way" 
> binding, which
> in effect means that I start observing the thing I'm bound to. In that
> thread I was concentrating on the downside, which is that the thing 
> I'm
> bound to does not automatically also start observing me; but now 
> let's talk
> about the upside. The upside is that my ivar gets set automatically 
> when the
> other object's observed attribute changes - without ever passing 
> through
> observeValue...!
>
> So, if what you were going to do was call setValue:forKey: on your 
> own ivar,
> you could skip the whole addObserver: thing and just use bind:, 
> because
> that's exactly what then *will* happen; setValue:forKey: will be 
> called on
> your ivar.


True. I guess if you want to avoid the KVO "bottleneck" you can just 
use "one way" bindings instead!

> Moreover, in the case of something like an NSController's 
> "content", this
> approach works, when ordinary observing with addObserver: does not. 
> As has
> been pointed out several times recently, the change dictionary 
> passed to
> observeValue... is empty. But if you start with bind:, it works 
> great; the
> new value just gets handed to you directly.


Is this right?. If you bind to "arrangedObjects" the entire array is 
sent each time it is modified. I tried binding to "content" and 
wasn't getting any updates on modifications so maybe my test was 
wrong anyhow. But it doesn't look like you can get just the change/
removed values using bind.

> Of course this is officially a misuse of bindings,


I don't think implementing "one way" or "read only" bindings is a 
misuse, though it almost seems that way since there aren't any 
examples or mentions of it in the docs that I remember seeing. I 
think I'll file a doc request.
It does seem to be a sly way of avoiding the observeValueForKeyPath 
bottleneck though.

I think I better add a disclaimer since many details of this whole 
thing are still fuzzy in my head: Anything stated above may be 
completely wrong. There, I feel better. ;)

George

Related mailsAuthorDate
mlKVO and the observeValueForKeyPath bottleneck Matt Neuburg Jul 14, 19:44
mlRe: KVO and the observeValueForKeyPath bottleneck George Orthwein Jul 15, 07:36
mlRe: KVO and the observeValueForKeyPath bottleneck Aaron Burghardt Jul 15, 22:56
mlRe: KVO and the observeValueForKeyPath bottleneck Jakob Olesen Jul 17, 12:38
mlRe: KVO and the observeValueForKeyPath bottleneck Jakob Olesen Jul 17, 13:03
mlRe: KVO and the observeValueForKeyPath bottleneck Matt Neuburg Jul 17, 16:38
mlRe: KVO and the observeValueForKeyPath bottleneck Jakob Olesen Jul 17, 16:57
mlRe: KVO and the observeValueForKeyPath bottleneck Matt Neuburg Jul 17, 17:31
mlRe: KVO and the observeValueForKeyPath bottleneck Chris Kane Jul 17, 18:09
mlRe: KVO and the observeValueForKeyPath bottleneck Matt Neuburg Jul 17, 19:49
mlRe: Re: KVO and the observeValueForKeyPath bottleneck Michael Ash Jul 17, 20:11
mlRe: KVO and the observeValueForKeyPath bottleneck Chris Kane Jul 17, 20:24
mlRe: KVO and the observeValueForKeyPath bottleneck Matt Neuburg Jul 17, 20:31
mlRe: KVO and the observeValueForKeyPath bottleneck Scott Anguish Jul 17, 22:00
mlRe: KVO and the observeValueForKeyPath bottleneck Chris Kane Jul 17, 22:42
mlRe: KVO and the observeValueForKeyPath bottleneck Jakob Olesen Jul 17, 23:16
mlRe: KVO and the observeValueForKeyPath bottleneck Matt Neuburg Jul 18, 00:43
mlRe: KVO and the observeValueForKeyPath bottleneck Chris Kane Jul 18, 03:00
mlRe: KVO and the observeValueForKeyPath bottleneck Jim Correia Jul 18, 05:37
mlRe: KVO and the observeValueForKeyPath bottleneck Jakob Olesen Jul 18, 16:06
mlRe: KVO and the observeValueForKeyPath bottleneck Jim Correia Jul 18, 18:11
mlRe: KVO and the observeValueForKeyPath bottleneck Matt Neuburg Jul 19, 02:44
mlRe: KVO and the observeValueForKeyPath bottleneck George Orthwein Jul 20, 21:25
mlRe: KVO and the observeValueForKeyPath bottleneck Scott Anguish Jul 20, 22:14
mlRe: KVO and the observeValueForKeyPath bottleneck Matt Neuburg Jul 21, 03:57
mlRe: KVO and the observeValueForKeyPath bottleneck Scott Anguish Jul 21, 10:11
mlRe: KVO and the observeValueForKeyPath bottleneck George Orthwein Jul 21, 17:46
mlRe: KVO and the observeValueForKeyPath bottleneck Scott Anguish Jul 21, 23:01