Thread overview
nextPermutation: why possible for dchar but not for char?
Dec 28, 2013
Ivan Kazmenko
Dec 28, 2013
Ivan Kazmenko
Dec 28, 2013
monarch_dodra
Dec 29, 2013
Ivan Kazmenko
Dec 28, 2013
monarch_dodra
Dec 28, 2013
Ivan Kazmenko
Dec 29, 2013
monarch_dodra
Dec 29, 2013
Ivan Kazmenko
December 28, 2013
Another quick question, two of them.

1. This is a minimal example of trying the permutations of a character array.

-----
import std.algorithm;
void main () {
    char [] a;
    do { } while (nextPermutation(a));
}
-----

This gives a compile error.  However, it works when I change "char [] a" to "dchar [] a".  Why?

I understand that permuting a char [] array might be wrong way to go when dealing with Unicode.  But what if, at this point of the program, I am sure I'm dealing with ASCII and just want efficiency?  Should I convert to ubyte [] somehow - what's the expected way then?  The "cast (ubyte [])" works, but "to!(ubyte [])" fails at runtime, expecting a string representation of the array, not its raw contents.

2. Why does nextPermutation hang up for empty arrays?  I suppose that's a bug?

Ivan Kazmenko.
December 28, 2013
On Saturday, 28 December 2013 at 22:55:39 UTC, Ivan Kazmenko wrote:
> Another quick question, two of them.
>
> 1. This is a minimal example of trying the permutations of a character array.
>
> -----
> import std.algorithm;
> void main () {
>     char [] a;
>     do { } while (nextPermutation(a));
> }
> -----
>
> This gives a compile error.  However, it works when I change "char [] a" to "dchar [] a".  Why?
>
> I understand that permuting a char [] array might be wrong way to go when dealing with Unicode.  But what if, at this point of the program, I am sure I'm dealing with ASCII and just want efficiency?  Should I convert to ubyte [] somehow - what's the expected way then?  The "cast (ubyte [])" works, but "to!(ubyte [])" fails at runtime, expecting a string representation of the array, not its raw contents.
>
> 2. Why does nextPermutation hang up for empty arrays?  I suppose that's a bug?
>
> Ivan Kazmenko.

Also, the example at
http://dlang.org/phobos/std_algorithm.html#nextPermutation
is wrong:
while (nextPermutation(a)) { }
should in fact be
do { } while (nextPermutation(a));
as above, or we miss the very first permutation.
December 28, 2013
On Saturday, 28 December 2013 at 22:55:39 UTC, Ivan Kazmenko wrote:
> Another quick question, two of them.
>
> 1. This is a minimal example of trying the permutations of a character array.
>
> -----
> import std.algorithm;
> void main () {
>     char [] a;
>     do { } while (nextPermutation(a));
> }
> -----
>
> This gives a compile error.  However, it works when I change "char [] a" to "dchar [] a".  Why?
>
> I understand that permuting a char [] array might be wrong way to go when dealing with Unicode.  But what if, at this point of the program, I am sure I'm dealing with ASCII and just want efficiency?  Should I convert to ubyte [] somehow - what's the expected way then?

Because next permutation (AFAIK) works on ranges with *assignable* elements, and "char[]" is not such a range: It is a read-only range of dchars.

Arguably, the implementation *could* work for it, *even* while taking into consideration unicode (using the underlying UTF8 knowledge). You should file an ER for that. But currently, this is not the case, so you have to look for a workaround.

> The "cast (ubyte [])" works, but "to!(ubyte [])" fails at runtime, expecting a string representation of the array, not its raw contents.

You can use "representation" to "conveniently" transform a string/wstring/dstring to its corresponding numeric type (ubyte/ushort/uint). That *should* work.

"Unfortunatly", "to!T(string)" often does a parse. As convenient as it is, I think the added ambiguity makes it often wrong.

> 2. Why does nextPermutation hang up for empty arrays?  I suppose that's a bug?

I suppose so. Please file it. If it is deemed "illegal", at the very least, it should throw.

> Ivan Kazmenko.
December 28, 2013
On Saturday, 28 December 2013 at 22:58:43 UTC, Ivan Kazmenko wrote:
> Also, the example at
> http://dlang.org/phobos/std_algorithm.html#nextPermutation
> is wrong:
> while (nextPermutation(a)) { }
> should in fact be
> do { } while (nextPermutation(a));
> as above, or we miss the very first permutation.

Noted. I'll try to fix that in the comming days. Or if anybody else submits the pull, I'll merge it (*hint* *hint*, *wink*)
December 28, 2013
On Saturday, 28 December 2013 at 23:05:54 UTC, monarch_dodra wrote:
>> 1. This is a minimal example of trying the permutations of a character array.
>>
>> -----
>> import std.algorithm;
>> void main () {
>>    char [] a;
>>    do { } while (nextPermutation(a));
>> }
>> -----
>>
>> This gives a compile error.  However, it works when I change "char [] a" to "dchar [] a".  Why?
>
> Because next permutation (AFAIK) works on ranges with *assignable* elements, and "char[]" is not such a range: It is a read-only range of dchars.

Ouch, is it an exception hard-coded into the language itself?  I thought it's just the nextPermutation's parameter type restrictions which don't allow "char []"...

>> 2. Why does nextPermutation hang up for empty arrays?  I suppose that's a bug?
>
> I suppose so. Please file it. If it is deemed "illegal", at the very least, it should throw.

OK, will do that tomorrow (on Sunday).

>> Also, the example at
>> http://dlang.org/phobos/std_algorithm.html#nextPermutation
>> is wrong:
>> while (nextPermutation(a)) { }
>> should in fact be
>> do { } while (nextPermutation(a));
>> as above, or we miss the very first permutation.
>
> Noted. I'll try to fix that in the comming days. Or if anybody else submits the pull, I'll merge it (*hint* *hint*, *wink*)

Hmm, I'll look into how hard is that for a start...

Ivan Kazmenko.
December 29, 2013
On Saturday, 28 December 2013 at 23:38:38 UTC, Ivan Kazmenko wrote:
> Ouch, is it an exception hard-coded into the language itself?  I thought it's just the nextPermutation's parameter type restrictions which don't allow "char []"...

No, a "char[]" is just a "char[]" as far as the language is concerned[1]. However, for the *phobos* range abstraction, (the front/popFront/empty) primitives, a char[] is a range of dchars. Once you've defined char[] as such a range, it affects all of phobos.

It's critiqued every now and then, but overall, it has proven to increase code correctness, at the cost (sometimes) of rejecting code that might be incorrect. Long story short: If you want to handle UTF, you have to handle it *explicitly*. *I* think it is a good compromise.

[1] the *only* place (AFAIK) that dmd looks at a string as a range of dchars is in a "foreach(dchar c; s)" loop. But even then, if you don't specify "dchar", then c will default to char.
December 29, 2013
On Saturday, 28 December 2013 at 23:07:21 UTC, monarch_dodra wrote:
>> Also, the example at
>> http://dlang.org/phobos/std_algorithm.html#nextPermutation
>> is wrong:
>> while (nextPermutation(a)) { }
>> should in fact be
>> do { } while (nextPermutation(a));
>> as above, or we miss the very first permutation.
>
> Noted. I'll try to fix that in the comming days. Or if anybody else submits the pull, I'll merge it (*hint* *hint*, *wink*)

Here it is:
https://github.com/D-Programming-Language/phobos/pull/1822
Or should it have been done in a separate branch?..  The bugtracker (http://d.puremagic.com/issues/) seems to be down at the moment, so there's no issue associated with it.

Ivan Kazmenko.
December 29, 2013
>> 2. Why does nextPermutation hang up for empty arrays?  I suppose that's a bug?
>
> I suppose so. Please file it. If it is deemed "illegal", at the very least, it should throw.

My fault, i mis-used it.  The right behavior for ranges of size 0 and 1 is checked explicitly in the unittests.

Ivan Kazmenko.