On Tue, Oct 4, 2011 at 1:08 PM, Sven Van Caekenberghe <[email protected]> wrote:

>
> On 04 Oct 2011, at 12:52, Mariano Martinez Peck wrote:
>
> > Hi guys. If I tell you the selector is Dictionary >> #at:ifAbsentPut:
>  what would you expect the second parameter to be?  the value.
> > So, one would do:
> > Dictionary new at: #foo ifAbsentPut: 4
> >
> > But if you see Dictionary >>
> >
> > at: key ifAbsentPut: aBlock
> >     "Return the value at the given key.
> >     If key is not included in the receiver store the result
> >     of evaluating aBlock as new value."
> >
> >     ^ self at: key ifAbsent: [self at: key put: aBlock value]
> >
> > so it expects a Block. Ok, we are in Smalltalk, so implementing #value is
> enough.
> >
> > Well..the previous example works, but only because we have an ugly Object
> >> value  that returns self.
> > If I put instances of subclasses from ProtoObjects (proxies), that do not
> work anymore.
> >
> > So...my question is we do Dictionary at: #foo put: 4, why
> #at:ifAbsentPut:  expects a block and not directly the value?
> > in which case I need a block instead of the value object directly ?
>
> You are right, it feels a bit silly.
> However, have a look at the senders (there are many).
> Often the block holds an expensive operation when using the dictionary as a
> cache:
>
>        cache at: key ifAbsent: [ backEnd get: key ]
>
>
and what is the difference to do:

cache at: key ifAbsent: ( backEnd get: key )    (notice the parenthesis
instead of [])

[500 timesRepeat:[
Dictionary new at: #foo ifAbsentPut: [ CompiledMethod instanceCount ] ]]
timeToRun 7254

[500 timesRepeat:[
Dictionary new at: #foo ifAbsentPut:  (CompiledMethod instanceCount)  ]]
timeToRun 7294

gives me more or less the same...

Thanks



> Then it feels quite elegant.
>
> Sven
>
>
>


-- 
Mariano
http://marianopeck.wordpress.com

Reply via email to