[squeak-dev] #in: for collections
Bert Freudenberg
bert at freudenbergs.de
Sat Dec 26 11:20:00 UTC 2009
On 25.12.2009, at 14:50, Randal L. Schwartz wrote:
>
> #((1 2 true) (2 1 false)) do: [:row |
> [:a :b :r | "do something useful" ] valueWithArguments: row.
> ].
>
> Beware... if your row doesn't have exactly three values, you'll
> get an exception. If you don't want that, consider #valueWithPossibleArgs:
I've sometimes wished for a "reversed" valueWithArguments:, because I used it like Randal above, but felt it obfuscates the control flow. Here's one of my usages (1):
^[:tpService :tpConn :tpChannels |
tpChannels collect: [:channel |
TelepathyChannel
connection: tpConn dbusConnection
busName: tpService
objectPath: channel dbusPath]
] valueWithArguments: sharedActivity getChannels
which looks like it returns a block and makes it hard to follow what happens. It does look nicer than this though (2):
| args tpService tpConn tpChannels |
args := sharedActivity getChannels.
tpService := args first.
tpConn := args second.
tpChannels := args third.
^tpChannels collect: [:channel |
TelepathyChannel
connection: tpConn dbusConnection
busName: tpService
objectPath: channel dbusPath]
But I'd much rather write this (3):
sharedActivity getChannels in: [:tpService :tpConn :tpChannels |
tpChannels collect: [:channel |
TelepathyChannel
connection: tpConn dbusConnection
busName: tpService
objectPath: channel dbusPath]]
... however, #in: only works with single-argument blocks. Making #in: work with multi-arg blocks is of course possible but feels not right either. Does anybody have an idea for a better selector? Or another idea for how to code this?
In my example, "#getChannels" is an external library call returning an array, this is the code that converts the raw result into a proper object structure. You can argue that low-level code like this is okay to look like (2) but I'd say it doesn't have to ;)
- Bert -
More information about the Squeak-dev
mailing list
|