Thread overview
strange behavior in opApply
Jan 27, 2007
BCS
Jan 27, 2007
Frits van Bommel
request in args option for opApply
Jan 28, 2007
BCS
January 27, 2007
I think this is a bug. I am not sure, but it is really annoying.

The following code fails to compile:

struct Foo
{
 int opApply(int delegate(in int) dg)
 {
   for(int i = 0; i< 10; i++)
     if(int ret = dg(i>>2))
       return ret;
   return 0;
 }
}

void main()
{
 Foo f;
 int j=0;
 foreach(int i; f)
 {
   j+=i;
 }
}

The foreach body is turned into a delegate taking (inout int), but it is not marked as inout! I have a case where I'm trying to use opApply where it can't be inout. 

Is this a bug?


January 27, 2007
BCS wrote:
> The foreach body is turned into a delegate taking (inout int), but it is not marked as inout! I have a case where I'm trying to use opApply where it can't be inout.
> Is this a bug?

According to the spec, the signature of opApply must be "int opApply(int delegate(inout Type [, ...]) dg);", so it's actually a bug in your code that the delegate's parameter it isn't marked inout.

(unless of course you prefer to consider it a 'bug' in the spec that it's not allowed to be marked 'in' :) )

January 28, 2007
Reply to Frits,

> BCS wrote:
> 
>> The foreach body is turned into a delegate taking (inout int), but it
>> is not marked as inout! I have a case where I'm trying to use opApply
>> where it can't be inout. Is this a bug?
>
> According to the spec, the signature of opApply must be "int
> opApply(int delegate(inout Type [, ...]) dg);", so it's actually a bug
> in your code that the delegate's parameter it isn't marked inout.
> 

Hm.. Is that new? I shure, it used to allow "in".

> (unless of course you prefer to consider it a 'bug' in the spec that
> it's not allowed to be marked 'in' :) )
> 

Yeah, I guess I'll have to stick with that approach. What else am I to do in a "must not modify data" loop? Copy everything? Or what about a case like this:


class C
{
 char[] str;
 int opApply(int delegate(inout char[]) dg)
 {
   for(int i = 1; i<=str.length; i++)
     for(int ret = dg(str[0..i]))      // fails b/c slices aren't L-values
       return ret;
 }
}

Oh well, I guess I'll just have to find workarounds.