www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - foreach overloading

reply Morlan <home valentimex.com> writes:
The section 12.9 (page 380) in the TDPL books presents foreach overloading.
However the example shown is problematic because there is no
method of automatic initializing of the _root variable without which foreach
overloading cannot work properly (obviously the loop steering
variable has to be initialized each time the loop is created). I tried to
consult the language reference but the section devoted to
operator overloading does not have any information about foreach overloading.
Where can I find definitive information about this feature?
What is the reason for discrepancy between TDPL book and the web language
reference?
Apr 03 2011
parent Jonathan M Davis <jmdavisProg gmx.com> writes:
On 2011-04-03 23:58, Morlan wrote:
 The section 12.9 (page 380) in the TDPL books presents foreach overloading.
 However the example shown is problematic because there is no method of
 automatic initializing of the _root variable without which foreach
 overloading cannot work properly (obviously the loop steering variable has
 to be initialized each time the loop is created). I tried to consult the
 language reference but the section devoted to operator overloading does
 not have any information about foreach overloading. Where can I find
 definitive information about this feature? What is the reason for
 discrepancy between TDPL book and the web language reference?

I think that you're taking the term "foreach overloading" a bit too literally. The two ways to get your type to work with foreach are to make it an input range (so, it defines the primitives front, popFront, and empty), or to have it define opApply. TDPL explains this. There is no overloaded operator for foreach. The example on p.380 is only attempting to show you the necessary primitives to make the type work with foreach, not define the entire type (hence why it doesn't do anything about initializing _root). Notice the ... after the definition for popFront. When foreach is used on a type which defines the primitives for an input range, the loop gets translated from foreach(i; range) { //... } to for(; !range.empty; range.popFront()) { auto i = range.front; //... } The range is then consumed by the foreach loop. The containers in std.container overload opSlice to return a range over their elements, and that would be a typical way to get a range over a container. - Jonathan M Davis
Apr 04 2011