www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - Error: shadowing declaration is deprecated

reply jicman <jic mail.com> writes:
Greetings!

this code,

  foreach(char[] u; FPUsers)
  {

  }

results in,

Error: shadowing declaration jic.libs.FPSDK.FindUser.u is deprecated.

Will anyone explain this to me?  I tried to do a search on it, but I couldn't
anything related to this.  Found other integer arrays, but nothing about
char[].  Any help would be greatly appreciated.  Thanks.

josé
Dec 23 2006
next sibling parent reply Bill Baxter <dnewsgroup billbaxter.com> writes:
jicman wrote:
 Greetings!
 
 this code,
 
   foreach(char[] u; FPUsers)
   {
 
   }
 
 results in,
 
 Error: shadowing declaration jic.libs.FPSDK.FindUser.u is deprecated.
 
 Will anyone explain this to me?  I tried to do a search on it, but I couldn't
 anything related to this.  Found other integer arrays, but nothing about
 char[].  Any help would be greatly appreciated.  Thanks.
 
 jos�

It means you have another variable named 'u' in the same function declared somewhere before that foreach loop. The theory is that many times these are bugs, and when they are they can be hard to spot. I'm not totally enamored with the feature myself, since I don't recall ever really been bitten by it, but I have happily shadowed variables in the past when it suited me. Especially little dummy counter/placeholder variables like your 'c' above. But anyway, that's what the error means. Just rename 'c' to c2 or cc or d. --bb
Dec 23 2006
parent reply jicman <jic mail.com> writes:
== Quote from Bill Baxter's article
 jicman wrote:
 Greetings!

 this code,

   foreach(char[] u; FPUsers)
   {

   }

 results in,

 Error: shadowing declaration jic.libs.FPSDK.FindUser.u is


 Will anyone explain this to me?  I tried to do a search on it,


 anything related to this.  Found other integer arrays, but


 char[].  Any help would be greatly appreciated.  Thanks.

 jos�

declared somewhere before that foreach loop. The theory is that

 times these are bugs, and when they are they can be hard to spot.
 I'm not totally enamored with the feature myself, since I don't

 ever really been bitten by it, but I have happily shadowed

 the past when it suited me.  Especially little dummy

 variables like your 'c' above.
 But anyway, that's what the error means.  Just rename 'c' to c2 or

 --bb

Ok, I'll buy that, but this is not working either: char[] u; foreach(u; FPUsers) { } That should work.
Dec 24 2006
next sibling parent reply Ary Manzana <ary esperanto.org.ar> writes:
jicman escribió:
 == Quote from Bill Baxter's article
 jicman wrote:
 Greetings!

 this code,

   foreach(char[] u; FPUsers)
   {

   }

 results in,

 Error: shadowing declaration jic.libs.FPSDK.FindUser.u is


 Will anyone explain this to me?  I tried to do a search on it,


 anything related to this.  Found other integer arrays, but


 char[].  Any help would be greatly appreciated.  Thanks.

 jos�

declared somewhere before that foreach loop. The theory is that

 times these are bugs, and when they are they can be hard to spot.
 I'm not totally enamored with the feature myself, since I don't

 ever really been bitten by it, but I have happily shadowed

 the past when it suited me.  Especially little dummy

 variables like your 'c' above.
 But anyway, that's what the error means.  Just rename 'c' to c2 or

 --bb

Ok, I'll buy that, but this is not working either: char[] u; foreach(u; FPUsers) { } That should work.

But probably in your code there is some other variable "u" defined, previous to the "char[] u" line. Check that. Cheers, Ary
Dec 24 2006
parent reply %u <jic mail.com> writes:
== Quote from Ary Manzana (ary esperanto.org.ar)'s article
 jicman escribió:
 == Quote from Bill Baxter's article
 jicman wrote:
 Greetings!

 this code,

   foreach(char[] u; FPUsers)
   {

   }

 results in,

 Error: shadowing declaration jic.libs.FPSDK.FindUser.u is


 Will anyone explain this to me?  I tried to do a search on it,


 anything related to this.  Found other integer arrays, but


 char[].  Any help would be greatly appreciated.  Thanks.

 jos�




 declared somewhere before that foreach loop.  The theory is that

 times these are bugs, and when they are they can be hard to



 I'm not totally enamored with the feature myself, since I don't

 ever really been bitten by it, but I have happily shadowed

 the past when it suited me.  Especially little dummy

 variables like your 'c' above.
 But anyway, that's what the error means.  Just rename 'c' to c2



 cc or d.
 --bb

Ok, I'll buy that, but this is not working either: char[] u; foreach(u; FPUsers) { } That should work.

previous to the "char[] u" line. Check that. Cheers, Ary

Ok, let's take a look at this small program: void main() { char[][] tArr = null; tArr.length = tArr.length + 1; tArr[0] = "hi"; char[] u; foreach(u;tArr) printf(u); } As you can see, there are no other declaration of u in the program, and here is what I get when I use dmd: 0:56:01.67>dmd test.d test.d(7): Error: shadowing declaration test.main.u is deprecated Ok, what is it that I am not understanding.
Dec 24 2006
parent jicman <jic mail.com> writes:
Sorry, didn-t read the other posts.  ignore this post.


== Quote from %u (jic mail.com)'s article
 == Quote from Ary Manzana (ary esperanto.org.ar)'s article
 jicman escribió:
 == Quote from Bill Baxter's article
 jicman wrote:
 Greetings!

 this code,

   foreach(char[] u; FPUsers)
   {

   }

 results in,

 Error: shadowing declaration jic.libs.FPSDK.FindUser.u is


 Will anyone explain this to me?  I tried to do a search on





 but I couldn't
 anything related to this.  Found other integer arrays, but


 char[].  Any help would be greatly appreciated.  Thanks.

 jos�




 declared somewhere before that foreach loop.  The theory is




 many
 times these are bugs, and when they are they can be hard to



 I'm not totally enamored with the feature myself, since I




 recall
 ever really been bitten by it, but I have happily shadowed

 the past when it suited me.  Especially little dummy

 variables like your 'c' above.
 But anyway, that's what the error means.  Just rename 'c' to




 or
 cc or d.
 --bb

Ok, I'll buy that, but this is not working either: char[] u; foreach(u; FPUsers) { } That should work.



 previous to the "char[] u" line. Check that.
 Cheers,
 Ary

void main() { char[][] tArr = null; tArr.length = tArr.length + 1; tArr[0] = "hi"; char[] u; foreach(u;tArr) printf(u); } As you can see, there are no other declaration of u in the program, and here is what I get when I use dmd: 0:56:01.67>dmd test.d test.d(7): Error: shadowing declaration test.main.u is deprecated Ok, what is it that I am not understanding.

Sorr
Dec 24 2006
prev sibling next sibling parent BCS <BCS pathilink.com> writes:
jicman wrote:

 char[] u;
 foreach(u; FPUsers)
 {
 }
 
 That should work.

the u in the foreach is a new variable. thus it shadows the outer u.
Dec 24 2006
prev sibling parent reply Bill Baxter <dnewsgroup billbaxter.com> writes:
jicman wrote:
 == Quote from Bill Baxter's article
 jicman wrote:
 Greetings!

 this code,

   foreach(char[] u; FPUsers)
   {

   }

 results in,



 
 Ok, I'll buy that, but this is not working either:
 
 char[] u;
 foreach(u; FPUsers)
 {
 }
 
 That should work.

Ah ok, good point. This is because foreach(u; blah) is always taken to mean foreach(auto u; blah). It's a little special case to save some typing. I think it's a bad idea to have such a special case, but oh well. Now that you mention it I do remember ranting about this one at one point, but I wasn't annoyed enough by it to follow through. For one it means that you can't have a loop variable in a foreach that 'escapes', which eliminates some handy patterns like char[] u; foreach(u; FPUsers) { if match(u) break; } /* use u here */ Maybe there's some reason for this that has to do with how foreach is implemented for classes? But I don't see how that could be the case when this certainly works: char[] u; foreach(utmp; FPUsers) { u=utmp; if match(u) break; } /* use u here */ Anyway foreach could certainly be smarter than it is. For instance I believe the magic 'int' return value that opApply implementations must handle and diligently return back to their caller could be eliminated with some hidden variables on the stack. But Walter and others here don't seem to see that as a wart for some reason. --bb
Dec 24 2006
parent reply "Jarrett Billingsley" <kb3ctd2 yahoo.com> writes:
"Bill Baxter" <dnewsgroup billbaxter.com> wrote in message 
news:emn3rk$828$1 digitaldaemon.com...
 Ah ok, good point.  This is because foreach(u; blah) is always taken to 
 mean foreach(auto u; blah).   It's a little special case to save some 
 typing.  I think it's a bad idea to have such a special case, but oh well. 
 Now that you mention it I do remember ranting about this one at one point, 
 but I wasn't annoyed enough by it to follow through.  For one it means 
 that you can't have a loop variable in a foreach that 'escapes', which 
 eliminates some handy patterns like
    char[] u;
    foreach(u; FPUsers) { if match(u) break; }
    /* use u here */

 Maybe there's some reason for this that has to do with how foreach is 
 implemented for classes?  But I don't see how that could be the case when 
 this certainly works:
    char[] u;
    foreach(utmp; FPUsers) { u=utmp; if match(u) break; }
    /* use u here */

Foreach is implemented the same way for all types, not just classes -- the body is always converted to a delegate which is used as a callback in some kind of apply function. The indices are nothing but the parameter list for that delegate (which is why 'inout' is possible), hence this restriction. Your example works fine because nested functions can access outer function variables. In this case, u is an outer variable to the loop body. If you're wondering why foreach loops are implemented this way, it's because it's a very clever solution to some iteration problems. It makes it much easier to iterate through non-linear structures (like AAs), and it also doesn't require any allocation of an "iterator" object. All the iteration is performed by the apply function, which makes the most sense.
 Anyway foreach could certainly be smarter than it is.  For instance I 
 believe the magic 'int' return value that opApply implementations must 
 handle and diligently return back to their caller could be eliminated with 
 some hidden variables on the stack.  But Walter and others here don't seem 
 to see that as a wart for some reason.

That would be nice. It would just be a hidden variable in the enclosing function, and the foreach body would just set that result to the appropriate value before returning. It would still have to return something, though, to let the apply function know when to stop iterating. A bool would work fine.
Dec 24 2006
parent Bill Baxter <dnewsgroup billbaxter.com> writes:
Jarrett Billingsley wrote:
 "Bill Baxter" <dnewsgroup billbaxter.com> wrote in message 
 news:emn3rk$828$1 digitaldaemon.com...
 Ah ok, good point.  This is because foreach(u; blah) is always taken to 
 mean foreach(auto u; blah).   It's a little special case to save some 
 typing.  I think it's a bad idea to have such a special case, but oh well. 
 Now that you mention it I do remember ranting about this one at one point, 
 but I wasn't annoyed enough by it to follow through.  For one it means 
 that you can't have a loop variable in a foreach that 'escapes', which 
 eliminates some handy patterns like
    char[] u;
    foreach(u; FPUsers) { if match(u) break; }
    /* use u here */

 Maybe there's some reason for this that has to do with how foreach is 
 implemented for classes?  But I don't see how that could be the case when 
 this certainly works:
    char[] u;
    foreach(utmp; FPUsers) { u=utmp; if match(u) break; }
    /* use u here */

Foreach is implemented the same way for all types, not just classes -- the body is always converted to a delegate which is used as a callback in some kind of apply function. The indices are nothing but the parameter list for that delegate (which is why 'inout' is possible), hence this restriction. Your example works fine because nested functions can access outer function variables. In this case, u is an outer variable to the loop body.

My understanding is that it is implemented the same way for all types *except* for built-in arrays, which don't use the delegate mechanism and instead get transformed into something more like a for loop. Anyway, that's fine and all that it's implemented that way. It makes sense if you understand the implementation details. But to the casual user it's confusing that for and foreach appear to follow different rules with regard to variables declared outside the scope. In my opinion the compiler should do everything within reason to make them appear to have the same behavior. But maybe in this case nothing "within reason" is possible. Particularly when it comes to the inout there. Still feels to me like it could be better, but maybe not.
 Anyway foreach could certainly be smarter than it is.  For instance I 
 believe the magic 'int' return value that opApply implementations must 
 handle and diligently return back to their caller could be eliminated with 
 some hidden variables on the stack.  But Walter and others here don't seem 
 to see that as a wart for some reason.

That would be nice. It would just be a hidden variable in the enclosing function, and the foreach body would just set that result to the appropriate value before returning. It would still have to return something, though, to let the apply function know when to stop iterating. A bool would work fine.

To me passing that int value around in my opApply feels akin to manually manipulating vtable offests or something. It's an implementation detail that I shouldn't have to worry about, and is really too unsafe for me to be touching in the first place. --bb
Dec 24 2006
prev sibling parent BCS <BCS pathilink.com> writes:
jicman wrote:
 Greetings!
 
 this code,
 
   foreach(char[] u; FPUsers)
   {
 
   }
 
 results in,
 
 Error: shadowing declaration jic.libs.FPSDK.FindUser.u is deprecated.
 
 Will anyone explain this to me?  I tried to do a search on it, but I couldn't
 anything related to this.  Found other integer arrays, but nothing about
 char[].  Any help would be greatly appreciated.  Thanks.
 
 jos�
 

Code of the form { int a; { int a; } } is not allowed. check to see if there is another variable in scope called "u". It or the "u" from the foreach needs to be renamed.
Dec 23 2006