std.algorithm.remove and principle of least astonishment
Steven Schveighoffer
schveiguy at yahoo.com
Sat Oct 16 11:39:38 PDT 2010
On Sat, 16 Oct 2010 14:29:59 -0400, klickverbot <see at klickverbot.at> wrote:
> Hello all,
>
> I decided to have a go at solving some easy programming puzzles with
> D2/Phobos to see how Phobos, especially ranges and std.algorithm, work
> out in simple real-world use cases (the puzzle in question is from
> hacker.org, by the way).
>
> The following code is a direct translation of a simple problem
> description to D (it is horrible from performance point of view, but
> that's certainly no issue here).
>
> ---
> import std.algorithm;
> import std.conv;
> import std.stdio;
>
> // The original input string is longer, but irrelevant to this post.
> enum INPUT = "93752xxx746x27x1754xx90x93xxxxx238x44x75xx087509";
>
> void main() {
> uint sum;
>
> auto tmp = INPUT.dup;
> size_t i;
> while ( i < tmp.length ) {
> char c = tmp[ i ];
> if ( c == 'x' ) {
> tmp = remove( tmp, i );
> i -= 2;
> } else {
> sum += to!uint( [ c ] );
> ++i;
> }
> }
>
> writeln( sum );
> }
> ---
>
> Quite contrary to what you would expect, the call to »remove« fails to
> compile with the following error messages: »std/algorithm.d(4287):
> Error: front(src) is not an lvalue« and »std/algorithm.d(4287): Error:
> front(tgt) is not an lvalue«.
My guess is that since INPUT is a string, phobos has unwisely decided to
treat strings not as random access arrays of chars, but as a bidirectional
range of dchar. This means that even though you can randomly access the
characters (phobos can't take that away from you), it artificially imposes
restrictions (such as making front an rvalue) where it wouldn't do the
same to an int[] or ubyte[].
Andrei, I am increasingly seeing people struggling with the decision to
make strings bidirectional ranges of dchar instead of what the compiler
says they are. This needs a different solution. It's too
confusing/difficult to deal with.
I suggest wrapping a char[] or wchar[] (of all constancies) with a special
range that imposes the restrictions. This means people will have to use
these ranges when they want to treat them as bidir ranges of dchar, but
the current situation is at least annoying, if not a complete turn-off to
D. And it vastly simplifies code that uses ranges, since they now don't
have to contain special cases for char[] and wchar[].
-Steve
More information about the Digitalmars-d
mailing list