Hidden argument kind antipattern

spir denis.spir at gmail.com
Tue Apr 19 16:30:40 PDT 2011


On 04/20/2011 01:18 AM, dsimcha wrote:
> == Quote from Vladimir Panteleev (vladimir at thecybershadow.net)'s article
>> To elaborate, I mean allowing code which appears to behave surprisingly
>> different from the at-a-glance interpretation, unless the programmer knows
>> the function's signature. I've noticed a worrying adoption in D of this
>> "antipattern", which, frankly, I believe doesn't belong in a well-designed
>> programming language. One classic example of this is passing arguments by
>> reference, something D inherited from C++. For example:
>> int x, y;
>> // ...
>> someObject.updateCoords(x, y);
>> What can you say about this code? The unobvious and surprising
>> interpretation of it is that updateCoords will change the values of x and
>> y. C# solved this problem neatly by requiring to specify the "ref" keyword
>> before the function arguments:
>> someObject.updateCoords(ref x, ref y); // much clearer
>> This problem carries over to lazy parameters, as well. I'll quote a line
>> of code from a recent post by David Simcha:
>>> auto connections = taskPool.workerLocalStorage(new MysqlConnection());
>> Anyone who is not familiar with std.parallelism and D's lazy parameter
>> feature is going to be very surprised to find out what this code really
>> does. This might be OK for us, experienced D users, but think about the
>> poor bloke who will someday, somewhere try to debug a D program written by
>> someone else, and tear his hair out trying to figure out why an expression
>> passed as an argument to some function isn't being evaluated before/during
>> the function call. (The solution I would suggest is simply having to
>> specify the "lazy" keyword before the expression of each lazy parameter,
>> same as C#'s "ref". This will require updating all usage of "enforce"
>> among other changes.)
>> I know that I should have brought this up during the module's review
>> phase, so take the following with a grain of salt: in my opinion,
>> std.parallelism's usage of lazy parameters overreaches their intended use
>> and borders into abuse of this language feature. For this reason (and
>> meaning no disrespect towards David and everyone who participated in
>> shaping the module), I am uncomfortable with the inclusion of
>> std.parallelism into the standard D library, as it would carry the message
>> that D's maintainers encourage abusing the language in such ways. (This
>> probably doesn't count as a vote.) For the moment, I would suggest
>> changing all lazy parameters which are evaluated in different contexts
>> (outside of the said function) into delegates, and replacing their usage
>> with delegate literals.
>
> Interesting point.  I was questioning whether this was really a good idea myself.
>   I did it because it seemed like things like this were kind of the point of lazy
> parameters.  Let's have a good discussion on this now, and if we decide that my
> idiom is an abuse of lazy parameters, then I'll switch it over to a delegate
> literal.  My vote is weakly in favor of lazy parameters, since a maintenance
> programmer would probably look at what such a function does and not be surprised
> for very long.  However, I'm not dead-set against changing it if there's a strong
> consensus that it should be changed.

And what about requiring "lazy" (and "ref") at the call site; I mean in the 
long term? I find this very sensible.

Denis
-- 
_________________
vita es estrany
spir.wikidot.com



More information about the Digitalmars-d mailing list