On Thursday, January 20, 2011 16:12:58 Tomek Sowiński wrote: > Doing my own deeds, I often found myself in need of writing up a range just > to e.g. feed it into an algorithm. Problem is, defining even the simplest > range -- one-pass forward -- is verbose enough to render this (correct) > approach unprofitable. > > This is how I went about the problem: > > auto range(T, Whatever)(lazy bool _empty, lazy Whatever _popFront, lazy T > _front) { struct AdHocRange { > @property bool empty() { return _empty(); } > void popFront() { _popFront(); } > @property T front() { return _front(); } > } > return AdHocRange(); > } > > --- example --- > > try { ... } > catch(Throwable t) > { > auto r = range(t is null, t = t.next, t); > > // process exception chain... > } > > I don't know a terser way to get a full-fledged range. It comes at a cost, > though. Lazy parameters are just sugar over delegates, so it's not exactly > Usain Bolt**... And you can't return it because by bug or by design lazy > parameters (unlike vanilla delegates) don't work like closures. Still, > even with the overhead and limitations the idiom is remarkably useful, > especially in face of range-unfriendly libraries from outside D realm. > > Enjoy.
What types of stuff do you need ad-hoc ranges for? What's the use case? I've never actually needed such a thing. I'm curious. If it's really something that's likely to be generally useful, then a function similar to what you're suggesting probably should be added to std.range. - Jonathan M Davis