www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - Shout out to D at cppcon, when talkign about ranges.

reply deadalnix <deadalnix gmail.com> writes:
https://www.youtube.com/watch?v=mFUXNMfaciE

From
http://wiki.dlang.org/Component_programming_with_ranges

Congrat H. S. Teoh
Sep 29 2015
next sibling parent reply deadalnix <deadalnix gmail.com> writes:
On Wednesday, 30 September 2015 at 01:45:49 UTC, deadalnix wrote:
 https://www.youtube.com/watch?v=mFUXNMfaciE

 From
 http://wiki.dlang.org/Component_programming_with_ranges

 Congrat H. S. Teoh
Shared on reddit: https://www.reddit.com/r/programming/comments/3mwu4e/cppcon_2015_eric_niebler_ranges_for_the_standard/ Also disappointed by Herb talk. It was very interesting, but he was blatantly dishonest when comparing other languages. He goes to claim GC in other languages is costly (it is) but then goes to propose "cost free" smart pointer kind of solution that are not cost free. Many paper show how both solution are on a continuum and he MUST know this.
Sep 29 2015
parent Arjan <arjan ask.me.to> writes:
On Wednesday, 30 September 2015 at 01:55:43 UTC, deadalnix wrote:
 On Wednesday, 30 September 2015 at 01:45:49 UTC, deadalnix 
 wrote:
 https://www.youtube.com/watch?v=mFUXNMfaciE

 From
 http://wiki.dlang.org/Component_programming_with_ranges

 Congrat H. S. Teoh
Shared on reddit: https://www.reddit.com/r/programming/comments/3mwu4e/cppcon_2015_eric_niebler_ranges_for_the_standard/ Also disappointed by Herb talk. It was very interesting, but he was blatantly dishonest when comparing other languages. He goes to claim GC in other languages is costly (it is) but then goes to propose "cost free" smart pointer kind of solution that are not cost free. Many paper show how both solution are on a continuum and he MUST know this.
I had the same feeling, as a lot of the ideas clearly comes from languages (like D / Rust / ..) but were presented to the public as inventions of their own.
Sep 30 2015
prev sibling next sibling parent reply Freddy <Hexagonalstar64 gmail.com> writes:
On Wednesday, 30 September 2015 at 01:45:49 UTC, deadalnix wrote:
 https://www.youtube.com/watch?v=mFUXNMfaciE

 From
 http://wiki.dlang.org/Component_programming_with_ranges

 Congrat H. S. Teoh
So this is what APL feels like. /s
Sep 29 2015
parent Wyatt <wyatt.epp gmail.com> writes:
On Wednesday, 30 September 2015 at 02:59:40 UTC, Freddy wrote:
 So this is what APL feels like. /s
Nah, the APL version would be shorter and only use builtins. ;) -Wyatt
Sep 30 2015
prev sibling next sibling parent reply Steven Schveighoffer <schveiguy yahoo.com> writes:
On 9/29/15 9:45 PM, deadalnix wrote:
 https://www.youtube.com/watch?v=mFUXNMfaciE

 From
 http://wiki.dlang.org/Component_programming_with_ranges

 Congrat H. S. Teoh
Ditto! Here is the link to the video at the time where D is credited, very nice compliment: https://youtu.be/mFUXNMfaciE?t=115 -Steve
Sep 30 2015
parent reply Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
On 09/30/2015 09:31 AM, Steven Schveighoffer wrote:
 On 9/29/15 9:45 PM, deadalnix wrote:
 https://www.youtube.com/watch?v=mFUXNMfaciE

 From
 http://wiki.dlang.org/Component_programming_with_ranges

 Congrat H. S. Teoh
Ditto! Here is the link to the video at the time where D is credited, very nice compliment: https://youtu.be/mFUXNMfaciE?t=115 -Steve
One great action item is to backport some of Eric's ideas to the D example. Currently Eric's final code looks nicer than the D code. -- Andrei
Sep 30 2015
next sibling parent reply "H. S. Teoh via Digitalmars-d" <digitalmars-d puremagic.com> writes:
On Wed, Sep 30, 2015 at 10:32:16AM -0400, Andrei Alexandrescu via Digitalmars-d
wrote:
 On 09/30/2015 09:31 AM, Steven Schveighoffer wrote:
On 9/29/15 9:45 PM, deadalnix wrote:
https://www.youtube.com/watch?v=mFUXNMfaciE

From
http://wiki.dlang.org/Component_programming_with_ranges

Congrat H. S. Teoh
Ditto! Here is the link to the video at the time where D is credited, very nice compliment: https://youtu.be/mFUXNMfaciE?t=115
[...] I watched most of the video (mainly the first half where he goes through the C++ version of the code), and I have to confess I couldn't help noticing just how ugly the C++ syntax is. I mean, overloading operator|() for chaining, seriously? UFCS is superior any day, IMNSHO. And overloading operator%() for string interpolation, ugh. (Though this one seems to be a Boost thing, not specific to the ranges proposal.) And this is on top of the usual ugliness of C++ template syntax. Not to mention the RANGE_FOREACH macro (I assume it's a macro), where D's foreach has supported natively for years now. (D has seriously ruined my life; I simply can't bring myself to go back to C++ anymore. At least not voluntarily.) Also, this seems to confirm that C++ is gradually falling to the position where it's playing catch-up with respect to innovations in newer languages like D and Rust. The fact that ranges are being proposed for the C++ standard library is a big endorsement of D, IMO. It's also clear that the imperative crowd is slowly but surely moving towards a more functional approach to programming. As the presenter said, having mutable state and branching/looping is what makes code explode in combinatorial complexity, making it hard to analyse, hard to prove correct, and more prone to bugs. I feel like he didn't hit on the central point of my article, though. The whole thrust behind that article was the idea of impedance mismatch between code structure and data structure, an idea I picked up from the Jackson Structured Programming paradigm in my college years. When code structure and data structure don't map 1-to-1, there's a structure conflict, and the usual response is to invent ad hoc hacks to compensate for the mismatch, usually in the form of boolean flags or other such band-aids. JSP, however, proposes that the *right* way to resolving the conflict is to change the program structure so that it *does* match the structure of the data. I have applied this in various forms throughout my career, and have found that it works very well not only in solidifying the way I write loops, but it also gives me a tangible handle on how to better shape the large-scale of my programs. Where ranges come in, is that ranges, due to their modular, encapsulated nature and their standardized API, essentially guides the programmer into the correct data-matching code structure in an unobtrusive, even spontaneous manner. In order to make range-based code work at all, you pretty much have to write your code in a way that exactly matches your data -- hacks like boolean flags and other such ugliness are spontaneously excluded (unless you deliberately warp your code to bring them back in -- and who in their right mind would want to do that?). To me, this is what makes ranges such a great innovation: you get the best of JSP (which I suspect almost nobody these days has even heard about!), many of the benefits of pure functional programming, code readability, testability, etc., all in one package. And it's not even hard to use.
 One great action item is to backport some of Eric's ideas to the D
 example.  Currently Eric's final code looks nicer than the D code. --
 Andrei
Do you have a list of ideas that should be backported? One that I can think of is using transpose() to do the columnar pasting, instead of the more specific function that I wrote specifically for that purpose. That was very clever, since by making all the formatted months exactly the same dimensions, it avoided the need to write a specific function, but can simply use transpose(). Great idea indeed! T -- VI = Visual Irritation
Sep 30 2015
parent reply lobo <swamplobo gmail.com> writes:
On Wednesday, 30 September 2015 at 22:51:24 UTC, H. S. Teoh wrote:
 On Wed, Sep 30, 2015 at 10:32:16AM -0400, Andrei Alexandrescu
[...]
 I watched most of the video (mainly the first half where he 
 goes through the C++ version of the code), and I have to 
 confess I couldn't help noticing just how ugly the C++ syntax 
 is.
This is a key reason I am using D. I really like C++14+boost but that syntax brings me back to D every time.
 I mean, overloading operator|() for chaining, seriously?  UFCS 
 is
 superior any day, IMNSHO.
I seem to recall that in a previous on ranges Niebler said that operator|() was simply available and had a vague notion of chaining thanks to *nix shell. He went on to say it would probably need to change to get through the ISO committee. I hope it does. If the current plans for overloading operator.() get up I wonder how well it would fit as a replacement operator.
 And overloading operator%() for string interpolation, ugh. 
 (Though this
 one seems to be a Boost thing, not specific to the ranges 
 proposal.)
This is also a Python thing so it's quite prevelant in the wild. I find D's ~ much nicer, although minutely slower to type than %
 And this is on top of the usual ugliness of C++ template 
 syntax. Not to mention the RANGE_FOREACH macro (I assume it's a 
 macro), where D's foreach has supported natively for years now.
  (D has seriously ruined my life; I simply can't bring myself 
 to go back to C++ anymore. At least not voluntarily.)

 Also, this seems to confirm that C++ is gradually falling to 
 the position where it's playing catch-up with respect to 
 innovations in newer languages like D and Rust. The fact that 
 ranges are being proposed for the C++ standard library is a big 
 endorsement of D, IMO.
C++ has been playing catchup for the last 10 yrs and it's been an amazing transition for the language. If ranges are accepted into ISO C++ I can't imagine it would be long before for(auto e:range). [snip]
 One great action item is to backport some of Eric's ideas to 
 the D example.  Currently Eric's final code looks nicer than 
 the D code. -- Andrei
Do you have a list of ideas that should be backported?
I really liked the namespaces view:: and action:: because it is immediately clear just reading the code what was lazy and what was not. bye, lobo
Sep 30 2015
parent reply bitwise <bitwise.pvt gmail.com> writes:
On Thursday, 1 October 2015 at 00:42:43 UTC, lobo wrote:
 If ranges are accepted into ISO C++ I can't imagine it would be 
 long before for(auto e:range).
Special features are not necessary to do this. C++ for loop works on anything with begin()/end() functions. Real ranges could just be a pair of iterators, and lazy ranges could give out dummies: template<class T> struct iota { T first, last; iota(T first, T last) : first(first), last(last) {} T front() const { return first; } void popFront() { ++first; } bool empty() const { return first == last; } struct iterator { iota *_iota; bool operator!=(const iterator& that) const { assert(_iota == that._iota); return !_iota->empty(); } void operator++() { _iota->popFront(); } T operator*() const { return _iota->front(); } }; iterator begin() { return iterator{this}; } iterator end() { return iterator{this}; } }; int main(int argc, const char * argv[]) { for(int x : iota<int>(0, 5)) printf("%d ", x); return 0; } I don't think it would be that hard to make something this possible: for(int x : iota<int>(0, 5).to<take>(3)) printf("%d ", x); The iterator dummy could probably be generalized with a template. Bit
Sep 30 2015
parent reply bitwise <bitwise.pvt gmail.com> writes:
On Thursday, 1 October 2015 at 01:32:17 UTC, bitwise wrote:
 I don't think it would be that hard to make something this 
 possible:

 for(int x : iota<int>(0, 5).to<take>(3))
     printf("%d ", x);
Curiosity got the best of me: http://ideone.com/RoJxLa output doesn't show up for some reason, but it works. Bit
Sep 30 2015
parent reply lobo <swamplobo gmail.com> writes:
On Thursday, 1 October 2015 at 01:54:22 UTC, bitwise wrote:
 On Thursday, 1 October 2015 at 01:32:17 UTC, bitwise wrote:
 I don't think it would be that hard to make something this 
 possible:

 for(int x : iota<int>(0, 5).to<take>(3))
     printf("%d ", x);
Curiosity got the best of me: http://ideone.com/RoJxLa output doesn't show up for some reason, but it works. Bit
Yes, that's what we have always done with iterators. The point is users shouldn't have to write or instantiate iterators explicitly for any custom range. bye, lobo
Sep 30 2015
parent reply bitwise <bitwise.pvt gmail.com> writes:
On Thursday, 1 October 2015 at 02:53:25 UTC, lobo wrote:
 On Thursday, 1 October 2015 at 01:54:22 UTC, bitwise wrote:
 On Thursday, 1 October 2015 at 01:32:17 UTC, bitwise wrote:
 I don't think it would be that hard to make something this 
 possible:

 for(int x : iota<int>(0, 5).to<take>(3))
     printf("%d ", x);
Curiosity got the best of me: http://ideone.com/RoJxLa output doesn't show up for some reason, but it works. Bit
Yes, that's what we have always done with iterators. The point is users shouldn't have to write or instantiate iterators explicitly for any custom range. bye, lobo
I understand, but the C++ committee seems very conservative to me, so when it's this easy to add for(:) support by giving ranges begin()/end() functions, it makes me doubt they will actually change the language for it. Bit
Sep 30 2015
parent reply Eric Niebler <eniebler boost.org> writes:
On Thursday, 1 October 2015 at 04:08:00 UTC, bitwise wrote:
 I understand, but the C++ committee seems very conservative to 
 me, so when it's this easy to add for(:) support by giving 
 ranges begin()/end() functions, it makes me doubt they will 
 actually change the language for it.
As of C++11, C++ has the for(auto e:range) control structure you are looking for. I would be using it here except for one thing: in my proposal, begin() and end() don't have to return objects of the same type! begin() must return an iterator and end() must return something that is EqualityComparable with the iterator -- but it doesn't have to be an iterator. That makes many types of iterators vastly simpler to implement and more efficient at runtime. C++'s built-in range-based for(:) loop expects begin() and end() to return objects of the same type. The committee is already talking about loosening that constraint so that the ranges I'm proposing Just Work with the existing built-in looping construct. Until then, there is an ugly macro. It's a temporary hack, nothing more. Hope that clears things up. Eric P.S. I see lots of people here assuming that C++ is playing catch-up to D because D has ranges and C++ doesn't yet. That is ignoring the long history of ranges in C++. C++ got ranges in the form of the Boost.Range library by Thorsten Ottoson sometime in the early 00's. Andrei didn't implement D's ranges until many years after. The ranges idea is older than dirt. It's not a D invention.
Sep 30 2015
next sibling parent reply deadalnix <deadalnix gmail.com> writes:
On Thursday, 1 October 2015 at 05:47:25 UTC, Eric Niebler wrote:
 On Thursday, 1 October 2015 at 04:08:00 UTC, bitwise wrote:
 I understand, but the C++ committee seems very conservative to 
 me, so when it's this easy to add for(:) support by giving 
 ranges begin()/end() functions, it makes me doubt they will 
 actually change the language for it.
As of C++11, C++ has the for(auto e:range) control structure you are looking for. I would be using it here except for one thing: in my proposal, begin() and end() don't have to return objects of the same type! begin() must return an iterator and end() must return something that is EqualityComparable with the iterator -- but it doesn't have to be an iterator. That makes many types of iterators vastly simpler to implement and more efficient at runtime. C++'s built-in range-based for(:) loop expects begin() and end() to return objects of the same type. The committee is already talking about loosening that constraint so that the ranges I'm proposing Just Work with the existing built-in looping construct. Until then, there is an ugly macro. It's a temporary hack, nothing more. Hope that clears things up. Eric
That's good news !
 P.S. I see lots of people here assuming that C++ is playing 
 catch-up to D because D has ranges and C++ doesn't yet. That is 
 ignoring the long history of ranges in C++. C++ got ranges in 
 the form of the Boost.Range library by Thorsten Ottoson 
 sometime in the early 00's. Andrei didn't implement D's ranges 
 until many years after. The ranges idea is older than dirt. 
 It's not a D invention.
Well, yes and no. Sure I'm sure there are precedent for ranges, be it in C++ or even I'm sure one can find them in other languages. I'm sure someone in the 70s had something like ranges already. But for years, it was a fringe idea in the C++ world, the consensus being the iterator were enough. Meanwhile, D adopted the idea and ran with it, doing so, proving how powerful the concept is. Some may be bitter, but I'm actually happy that C++ is adopting ranges, as these are a great tool. As long as the Jobs "we reinvented hot water with shiny corners and it is a revolution" style of presenting things do not become the norm. On that note, I think Herb's pissed of a lot of people with his talk. On the other hand, I think you did a fine job.
Oct 01 2015
parent Ola Fosheim =?UTF-8?B?R3LDuHN0YWQ=?= writes:
On Thursday, 1 October 2015 at 07:37:28 UTC, deadalnix wrote:
 Well, yes and no. Sure I'm sure there are precedent for ranges, 
 be it in C++ or even I'm sure one can find them in other 
 languages. I'm sure someone in the 70s had something like 
 ranges already.
Yes, certainly in the 70s, but I would be surprised if something like it was not done for Lisp in the 60s? What D/C++ call ranges is iterators/generators. C++ mislabeled "table-pointers" as "iterators", which is a source for endless confusion. Co-routines, like the ones in Simula which was "stackless", can be viewed as a heavy async version of iterators/generators too. Adapters can be hooked up at runtime also (if speed is not a priority). So, "ranges" are very common, with varying syntax/performance.
Oct 05 2015
prev sibling next sibling parent reply Walter Bright <newshound2 digitalmars.com> writes:
On 9/30/2015 10:47 PM, Eric Niebler wrote:
 P.S. I see lots of people here assuming that C++ is playing catch-up to D
 because D has ranges and C++ doesn't yet. That is ignoring the long history of
 ranges in C++. C++ got ranges in the form of the Boost.Range library by
Thorsten
 Ottoson sometime in the early 00's. Andrei didn't implement D's ranges until
 many years after. The ranges idea is older than dirt. It's not a D invention.
Range iteration over arrays have been around in D since the beginning and a more general proposal first appears here: http://www.digitalmars.com/d/archives//12773.html and Matthew Wilson did his range library for D in 9/2004 (and one for C++, too). He said he was going to propose it for Boost, I don't know if he ever did. It does appear in his "Imperfect C++" book. Matthew, a bit to my frustration, would always implement the D ideas first for C++ :-) but I don't think they garnered any attention from the C++ community. news://news.digitalmars.com/rangelib Here's something I wrote to Matthew in Feb 2004: "I think ranges in D are the same thing as slices. C++ doesn't have slices, so ranges makes sense as a distinct object. In D, slices over a collection or array simply yield a subset collection or subset array, not a separate object, so I'm not sure what value they would add to D." I found a link to Thorsten's Boost range: http://www.boost.org/doc/libs/1_34_0/libs/range/doc/intro.html http://www.boost.org/doc/libs/1_34_0/libs/range/doc/range.html It returns an iterator, so I don't think it is what we'd consider a range to be today. Matthew's ranges had the following members: current advance is_open corresponding to front, popFront, and empty. So I'd say given what I can dig up, that D's ranges were more advanced than Boost's were at the time. Sadly, Matthew's work seems to have disappeared from the internets and his web sites have vanished (rangelib.org). Update: found it on web.archive.org! https://web.archive.org/web/20050427085507/http://rangelib.synesis.com.au/ Anyhow, this is what I could dig up in an hour or so.
Oct 01 2015
next sibling parent reply Walter Bright <newshound2 digitalmars.com> writes:
Ranges because a D core language feature with D 2.021 Nov 25, 2008.

Core language feature meaning it was no longer just a library construction, it 
was supported by foreach loops.

As a library feature, it appeared in D 2.008 Nov 27, 2007.
Oct 01 2015
parent Jack Stouffer <jack jackstouffer.com> writes:
On Thursday, 1 October 2015 at 09:25:37 UTC, Walter Bright wrote:
 Ranges because a D core language feature with D 2.021 Nov 25, 
 2008.

 Core language feature meaning it was no longer just a library 
 construction, it was supported by foreach loops.

 As a library feature, it appeared in D 2.008 Nov 27, 2007.
Please be excited to see ranges in C++20
Oct 01 2015
prev sibling next sibling parent reply Joakim <dlang joakim.fea.st> writes:
On Thursday, 1 October 2015 at 08:37:37 UTC, Walter Bright wrote:
 Sadly, Matthew's work seems to have disappeared from the 
 internets and his web sites have vanished (rangelib.org).

 Update: found it on web.archive.org!

 https://web.archive.org/web/20050427085507/http://rangelib.synesis.com.au/

 Anyhow, this is what I could dig up in an hour or so.
That site is still up, at least for me: http://rangelib.synesis.com.au/
Oct 01 2015
parent Walter Bright <newshound2 digitalmars.com> writes:
On 10/1/2015 2:31 AM, Joakim wrote:
 On Thursday, 1 October 2015 at 08:37:37 UTC, Walter Bright wrote:
 Sadly, Matthew's work seems to have disappeared from the internets and his web
 sites have vanished (rangelib.org).

 Update: found it on web.archive.org!

 https://web.archive.org/web/20050427085507/http://rangelib.synesis.com.au/

 Anyhow, this is what I could dig up in an hour or so.
That site is still up, at least for me: http://rangelib.synesis.com.au/
I have the Oct 2004 issue of CUJ where Matthew Wilson writes about ranges: "Ranges are simple to use and implement and, for most of the components written so far, are compilable by a majority of commonly used compilers. They're so simple that you may wonder why no one has defined them before." Boost ranges are still not modern ranges: http://www.boost.org/doc/libs/1_59_0/libs/range/doc/html/range/concepts/single_pass_range.html Eric's ranges are modern ranges for C++. Matthew had them for C++ 10 years ago, but his work was forgotten. He was going to propose it for Boost, but I don't know what happened.
Oct 01 2015
prev sibling parent reply =?UTF-8?Q?Ali_=c3=87ehreli?= <acehreli yahoo.com> writes:
On 10/01/2015 01:37 AM, Walter Bright wrote:

 Update: found it on web.archive.org!

 
https://web.archive.org/web/20050427085507/http://rangelib.synesis.com.au/
 Anyhow, this is what I could dig up in an hour or so.
Thank you for mining for that. From the days that I used to frequent comp.lang.c++.moderated (before around 2009 or so), I remember an individual who was trying to sell the idea of ranges to the C++ community. As I remember, nobody took him seriously at that time. Reading the page above, I think that individual must have been John Torjo or Matthew Wilson. Ali
Oct 01 2015
parent reply Walter Bright <newshound2 digitalmars.com> writes:
On 10/1/2015 11:18 AM, Ali Çehreli wrote:
  From the days that I used to frequent comp.lang.c++.moderated (before around
 2009 or so), I remember an individual who was trying to sell the idea of ranges
 to the C++ community. As I remember, nobody took him seriously at that time.
 Reading the page above, I think that individual must have been John Torjo or
 Matthew Wilson.
It was Andrei's talk "Iterators Must Go" that was the turning point for C++ to start paying attention to ranges. C++ was inspirational to D in the foundational work with iterators. But iterators are not ranges, and I don't see evidence that C++ had ranges before D. Boost ranges are not what we think of as ranges. It is true that Matthew first implemented ranges in C++, and then D. But the C++ version never got any interest from the C++ community, and went nowhere. I am credited with helping Matthew in the CUJ article talking about his range library. What I helped with was a D design, which he then implemented in C++ :-( There's probably more in the thousands of emails I have, but I don't want to spend more time spelunking them.
Oct 01 2015
parent reply Eric Niebler <eniebler boost.org> writes:
On Thursday, 1 October 2015 at 21:03:16 UTC, Walter Bright wrote:
 I don't see evidence that C++ had ranges before D. Boost ranges 
 are not what we think of as ranges.
Why not?
Oct 02 2015
parent reply Walter Bright <newshound2 digitalmars.com> writes:
On 10/2/2015 10:49 AM, Eric Niebler wrote:
 On Thursday, 1 October 2015 at 21:03:16 UTC, Walter Bright wrote:
 I don't see evidence that C++ had ranges before D. Boost ranges are not what
 we think of as ranges.
Why not?
Because it returns iterators. It should expose functions (or operators) that do this: front popFront empty not iterators. Instead, it has: begin end empty The begin and end are iterators, and don't encapsulate (i.e. constrain) what can be done with those iterators. For example, begin can return an iterator that can be used to increment right on past the end. The iterator itself has no knowledge of where the end is. This is the issue that D ranges (and Matthew's and your's) solve. I believe the difference is fundamental. http://www.boost.org/doc/libs/1_34_0/libs/range/doc/range.html It's possible I misunderstand it, please correct me if so.
Oct 02 2015
next sibling parent Steven Schveighoffer <schveiguy yahoo.com> writes:
On 10/2/15 6:57 PM, Walter Bright wrote:
 On 10/2/2015 10:49 AM, Eric Niebler wrote:
 On Thursday, 1 October 2015 at 21:03:16 UTC, Walter Bright wrote:
 I don't see evidence that C++ had ranges before D. Boost ranges are
 not what
 we think of as ranges.
Why not?
Because it returns iterators. It should expose functions (or operators) that do this: front popFront empty not iterators. Instead, it has: begin end empty The begin and end are iterators, and don't encapsulate (i.e. constrain) what can be done with those iterators. For example, begin can return an iterator that can be used to increment right on past the end. The iterator itself has no knowledge of where the end is.
The solution to this is cursors. i.e. ranges that point at exactly one element. All dcollection ranges have begin and end accessors for cursors to the first and one beyond the last element, but unlike iterators you cannot do anything dangerous with them. What you CAN do, is construct ranges from them safely (there is a slight cost for this). The interface is much superior IMO to how containers do ranges in std.container. There is a deficiency in ranges in that they are very fragile when it comes to pointing at one element. Iterators are much better in this regard. -Steve
Oct 05 2015
prev sibling parent reply Eric Niebler <eniebler boost.org> writes:
On Friday, 2 October 2015 at 22:57:52 UTC, Walter Bright wrote:
 On 10/2/2015 10:49 AM, Eric Niebler wrote:
 On Thursday, 1 October 2015 at 21:03:16 UTC, Walter Bright 
 wrote:
 I don't see evidence that C++ had ranges before D. Boost 
 ranges are not what
 we think of as ranges.
Why not?
Because it returns iterators. It should expose functions (or operators) that do this: front popFront empty not iterators. Instead, it has: begin end empty The begin and end are iterators, and don't encapsulate (i.e. constrain) what can be done with those iterators. For example, begin can return an iterator that can be used to increment right on past the end. The iterator itself has no knowledge of where the end is.
For a D range, what happens if you popFront from an empty range? An assertion, I'm guessing. It is not hard for a C++ iterator to do the same, and many debug standard libraries have iterators that do that.
 This is the issue that D ranges (and Matthew's and your's) 
 solve. I believe the difference is fundamental.
A C++ iterator can store a pointer back to its range and implement all its core functionality in terms of simple operations like current, next, and done. The Boost.Iterators and Boost.Range libraries made that possible and have been around a long time. Some iterators can be implemented more efficiently without an indirection to the range. Those iterators are unsafe in the way you describe. The win is that iterators are a more powerful basis for building algorithms (i.e., you can express more with them).
 http://www.boost.org/doc/libs/1_34_0/libs/range/doc/range.html

 It's possible I misunderstand it, please correct me if so.
Oct 05 2015
parent reply Walter Bright <newshound2 digitalmars.com> writes:
On 10/5/2015 9:39 AM, Eric Niebler wrote:
 On Friday, 2 October 2015 at 22:57:52 UTC, Walter Bright wrote:
 The begin and end are iterators, and don't encapsulate (i.e. constrain) what
 can be done with those iterators. For example, begin can return an iterator
 that can be used to increment right on past the end. The iterator itself has
 no knowledge of where the end is.
For a D range, what happens if you popFront from an empty range? An assertion, I'm guessing.
You'd be right, and this is easy to do because a range encapsulates this knowledge.
 It is not hard for a C++ iterator to do the same, and many debug
 standard libraries have iterators that do that.


 This is the issue that D ranges (and Matthew's and your's) solve. I believe
 the difference is fundamental.
A C++ iterator can store a pointer back to its range and implement all its core functionality in terms of simple operations like current, next, and done. The Boost.Iterators and Boost.Range libraries made that possible and have been around a long time. Some iterators can be implemented more efficiently without an indirection to the range. Those iterators are unsafe in the way you describe.
Yes, you can build debug iterators that know their limits, or iterators with back pointers to the range. This is not an inherent property of Boost ranges, does not appear in the Boost description of ranges (unless I missed it), and is a kludge. I do not agree that D ranges owe anything to that design. In fact, it looks like an attempt to make iterators themselves ranges, rendering the Boost:range rather pointless?
Oct 05 2015
parent reply Eric Niebler <eniebler boost.org> writes:
On Monday, 5 October 2015 at 21:57:31 UTC, Walter Bright wrote:
 Yes, you can build debug iterators that know their limits, or 
 iterators with back pointers to the range. This is not an 
 inherent property of Boost ranges, does not appear in the Boost 
 description of ranges (unless I missed it), and is a kludge. I 
 do not agree that D ranges owe anything to that design.
The design of the D ranges and algorithms owe quite a lot to C++, and I've heard Andrei say as much. Stepanov did the hard work of defining common algorithms in terms of iterators of different strength. Given that starting point, ranges of different strength are an "obvious" next step that many people thought up independently. D took it one way and C++ went another. When designing my range library, I looked at all the prior art available to me including D ranges and decided D's path was not the right one for C++. My work is based on Boost.Range. I only posted here to clear up what appeared to me to be confusion about that. \e
Oct 05 2015
next sibling parent Jonathan M Davis <jmdavisProg gmx.com> writes:
On Tuesday, 6 October 2015 at 02:31:53 UTC, Eric Niebler wrote:
 On Monday, 5 October 2015 at 21:57:31 UTC, Walter Bright wrote:
 Yes, you can build debug iterators that know their limits, or 
 iterators with back pointers to the range. This is not an 
 inherent property of Boost ranges, does not appear in the 
 Boost description of ranges (unless I missed it), and is a 
 kludge. I do not agree that D ranges owe anything to that 
 design.
The design of the D ranges and algorithms owe quite a lot to C++, and I've heard Andrei say as much. Stepanov did the hard work of defining common algorithms in terms of iterators of different strength. Given that starting point, ranges of different strength are an "obvious" next step that many people thought up independently. D took it one way and C++ went another.
D's ranges and their use in D's standard library owe a _lot_ to C++ - especially to the STL. They just don't owe anything to Boost's ranges. They're two different paths from the same root.
 When designing my range library, I looked at all the prior art 
 available to me including D ranges and decided D's path was not 
 the right one for C++. My work is based on Boost.Range.
It'll be interesting to see where that goes. - Jonathan M Davis
Oct 05 2015
prev sibling next sibling parent reply Ulrich Kuettler <kuettler gmail.com> writes:
On Tuesday, 6 October 2015 at 02:31:53 UTC, Eric Niebler wrote:
 On Monday, 5 October 2015 at 21:57:31 UTC, Walter Bright wrote:
 Yes, you can build debug iterators that know their limits, or 
 iterators with back pointers to the range. This is not an 
 inherent property of Boost ranges, does not appear in the 
 Boost description of ranges (unless I missed it), and is a 
 kludge. I do not agree that D ranges owe anything to that 
 design.
The design of the D ranges and algorithms owe quite a lot to C++, and I've heard Andrei say as much. Stepanov did the hard work of defining common algorithms in terms of iterators of different strength.
There is no denying that D owns a lot to C++. Then again D comes with great ideas of its own and success has many fathers.
 Given that starting point, ranges of different strength are an 
 "obvious" next step that many people thought up independently. 
 D took it one way and C++ went another.

 When designing my range library, I looked at all the prior art 
 available to me including D ranges and decided D's path was not 
 the right one for C++.
What is your thinking here? Did you write it down somewhere? This would be very interesting.
 My work is based on Boost.Range. I only posted here to clear up 
 what appeared to me to be confusion about that.

 \e
Oct 05 2015
parent reply Jonathan M Davis <jmdavisProg gmx.com> writes:
On Tuesday, 6 October 2015 at 06:52:13 UTC, Ulrich Kuettler wrote:
 On Tuesday, 6 October 2015 at 02:31:53 UTC, Eric Niebler wrote:
 Given that starting point, ranges of different strength are an 
 "obvious" next step that many people thought up independently. 
 D took it one way and C++ went another.

 When designing my range library, I looked at all the prior art 
 available to me including D ranges and decided D's path was 
 not the right one for C++.
What is your thinking here? Did you write it down somewhere? This would be very interesting.
Obviously, Eric would have to respond for us to know what his reasoning was, but I expect that it least part of it stems from the fact that C++ already uses iterators heavily. So, having a range-based solution that doesn't interact with iterators (like D has) doesn't fit in well with the existing code and paradigms. Even if you were to assume that D's approach is superior (which is debatable), that doesn't mean that it's a good fit for C++. D has the advantage of having considerably less baggage to deal with, so we have more freedom in the direction that we go. Whether we go in the right direction or not is another matter, but C++ has considerably more constraints than we have, so it's no surprise if we end up with different solutions. - Jonathan M Davis
Oct 06 2015
parent reply Ulrich =?UTF-8?B?S8O8dHRsZXI=?= <kuettler gmail.com> writes:
On Tuesday, 6 October 2015 at 07:09:21 UTC, Jonathan M Davis 
wrote:
 On Tuesday, 6 October 2015 at 06:52:13 UTC, Ulrich Kuettler 
 wrote:
 On Tuesday, 6 October 2015 at 02:31:53 UTC, Eric Niebler wrote:
 Given that starting point, ranges of different strength are 
 an "obvious" next step that many people thought up 
 independently. D took it one way and C++ went another.

 When designing my range library, I looked at all the prior 
 art available to me including D ranges and decided D's path 
 was not the right one for C++.
What is your thinking here? Did you write it down somewhere? This would be very interesting.
Obviously, Eric would have to respond for us to know what his reasoning was, but I expect that it least part of it stems from the fact that C++ already uses iterators heavily. So, having a range-based solution that doesn't interact with iterators (like D has) doesn't fit in well with the existing code and paradigms. Even if you were to assume that D's approach is superior (which is debatable), that doesn't mean that it's a good fit for C++. D has the advantage of having considerably less baggage to deal with, so we have more freedom in the direction that we go. Whether we go in the right direction or not is another matter, but C++ has considerably more constraints than we have, so it's no surprise if we end up with different solutions.
Yes, this is an explanation. Thanks. So the argument being C++ customs. Now that you mention it, this seems to be the argument in Eric's D4128 paper, too. I was hoping for a somewhat deeper reasoning. Out of curiously, I am still trying to grasp all the implications. Ranges are hard.
Oct 06 2015
parent reply Trass3r <un known.com> writes:
On Tuesday, 6 October 2015 at 22:39:01 UTC, Ulrich Küttler wrote:
 Yes, this is an explanation. Thanks. So the argument being C++ 
 customs. Now that you mention it, this seems to be the argument 
 in Eric's D4128 paper, too.

 I was hoping for a somewhat deeper reasoning. Out of curiously, 
 I am still trying to grasp all the implications. Ranges are 
 hard.
Another one is "odd number of iterators algorithms"
 http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4128.html#appendix-3-d-ranges-and-algorithmic-complexity
 D’s choice of algorithmic basis operations is inherently less 
 efficient than C++’s.
Oct 07 2015
next sibling parent reply John Colvin <john.loughran.colvin gmail.com> writes:
On Wednesday, 7 October 2015 at 14:59:28 UTC, Trass3r wrote:
 On Tuesday, 6 October 2015 at 22:39:01 UTC, Ulrich Küttler 
 wrote:
 Yes, this is an explanation. Thanks. So the argument being C++ 
 customs. Now that you mention it, this seems to be the 
 argument in Eric's D4128 paper, too.

 I was hoping for a somewhat deeper reasoning. Out of 
 curiously, I am still trying to grasp all the implications. 
 Ranges are hard.
Another one is "odd number of iterators algorithms"
 http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4128.html#appendix-3-d-ranges-and-algorithmic-complexity
 D’s choice of algorithmic basis operations is inherently less 
 efficient than C++’s.
Hmm. That seems really contrived and/or missing the point. You would never design a function like that for use with ranges, but that doesn't mean you're any less able to efficiently find word boundaries using ranges.
Oct 07 2015
parent reply Jonathan M Davis <jmdavisProg gmx.com> writes:
On Wednesday, 7 October 2015 at 16:33:21 UTC, John Colvin wrote:
 On Wednesday, 7 October 2015 at 14:59:28 UTC, Trass3r wrote:
 On Tuesday, 6 October 2015 at 22:39:01 UTC, Ulrich Küttler 
 wrote:
 Yes, this is an explanation. Thanks. So the argument being 
 C++ customs. Now that you mention it, this seems to be the 
 argument in Eric's D4128 paper, too.

 I was hoping for a somewhat deeper reasoning. Out of 
 curiously, I am still trying to grasp all the implications. 
 Ranges are hard.
Another one is "odd number of iterators algorithms"
 http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4128.html#appendix-3-d-ranges-and-algorithmic-complexity
 D’s choice of algorithmic basis operations is inherently less 
 efficient than C++’s.
Hmm. That seems really contrived and/or missing the point. You would never design a function like that for use with ranges, but that doesn't mean you're any less able to efficiently find word boundaries using ranges.
As I understand it, there are algorithms that inherently need 3 iterators to do whatever is they do, and the question of how to deal with them has come up before in the newsgroup. I think that it's pretty clear that such algorithms are relatively few in number, but they do exist, and solving them with ranges does get potentially awkward. Similarly, using iterators with containers when you have to pass them to the container generally works better than ranges do. We've had to add overloads to the std.container types which take the results of the various take functions in order to work around that problem. So, there are clearly cases where ranges become awkward and iterators aren't. On the other hand, when dealing with algorithms, ranges tend to be far cleaner - especially when you need to chain them. And they tend to form a better basis of how to think about algorithms (even when dealing with iterators, you pretty much have to think in terms of ranges on some level at least). And ranges handle laziness far better than iterators do. So, I'm not the least bit convinced that iterators are a better way to go (quite the opposite), and I'm not convinced that trying to mix iterators and ranges is at all a good idea. But I do think that it's clear that using only ranges is not without its downsides, and since we're the first folks to seriously use ranges heavily in a language or standard library, we're bound to be making mistakes due to inexperience. At this point, I would guess that trying to mix iterators and ranges is just going to over-complicate things in an already over-complicated language, but it may actually be a big win for the C++ folks. We'll have to wait and see. If we _were_ to look at doing something more than straight ranges, we'd probably look more at something like Steven's cursors than adding iterators, though I think that there's a decent chance that that only really helps with containers (it's been a while since I looked at what he did with cursors, and I really don't remember the details), though for the most part, I think that containers are the primary place where ranges tend to get annoying. Algorithms where they're problematic do exist, but they seem to be rare. - Jonathan M Davis
Oct 07 2015
next sibling parent John Colvin <john.loughran.colvin gmail.com> writes:
On Wednesday, 7 October 2015 at 17:13:45 UTC, Jonathan M Davis 
wrote:
 As I understand it, there are algorithms that inherently need 3 
 iterators to do whatever is they do, and the question of how to 
 deal with them has come up before in the newsgroup. I think 
 that it's pretty clear that such algorithms are relatively few 
 in number, but they do exist, and solving them with ranges does 
 get potentially awkward. Similarly, using iterators with 
 containers when you have to pass them to the container 
 generally works better than ranges do. We've had to add 
 overloads to  the std.container types which take the results of 
 the various take functions in order to work around that 
 problem. So, there are clearly cases where ranges become 
 awkward and iterators aren't.

 On the other hand, when dealing with algorithms, ranges tend to 
 be far cleaner - especially when you need to chain them. And 
 they tend to form a better basis of how to think about 
 algorithms (even when dealing with iterators, you pretty much 
 have to think in terms of ranges on some level at least). And 
 ranges handle laziness far better than iterators do. So, I'm 
 not the least bit convinced that iterators are a better way to 
 go (quite the opposite), and I'm not convinced that trying to 
 mix iterators and ranges is at all a good idea. But I do think 
 that it's clear that using only ranges is not without its 
 downsides, and since we're the first folks to seriously use 
 ranges heavily in a language or standard library, we're bound 
 to be making mistakes due to inexperience. At this point, I 
 would guess that trying to mix iterators and ranges is just 
 going to over-complicate things in an already over-complicated 
 language, but it may actually be a big win for the C++ folks. 
 We'll have to wait and see.

 If we _were_ to look at doing something more than straight 
 ranges, we'd probably look more at something like Steven's 
 cursors than adding iterators, though I think that there's a 
 decent chance that that only really helps with containers (it's 
 been a while since I looked at what he did with cursors, and I 
 really don't remember the details), though for the most part, I 
 think that containers are the primary place where ranges tend 
 to get annoying. Algorithms where they're problematic do exist, 
 but they seem to be rare.

 - Jonathan M Davis
Couldn't we define a TriRange or something for this?
Oct 07 2015
prev sibling next sibling parent Timon Gehr <timon.gehr gmx.ch> writes:
On 10/07/2015 07:13 PM, Jonathan M Davis wrote:
 ...

 If we _were_ to look at doing something more than straight ranges, we'd
 probably look more at something like Steven's cursors than adding
 iterators, though I think that there's a decent chance that that only
 really helps with containers (it's been a while since I looked at what
 he did with cursors, and I really don't remember the details), though
 for the most part, I think that containers are the primary place where
 ranges tend to get annoying. Algorithms where they're problematic do
 exist, but they seem to be rare.

 - Jonathan M Davis
I think the most obvious way to generalize, such that ranges cater to those use cases, is to introduce a type of range that additionally requires the primitives: full(); // pushFront cannot be called unless false pushFront(); // restores one element at the front of the range The idea is: auto r=..., s=r.save; assert(r.full); r.popFront(); assert(!r.full); r.pushFront(); assert(r.full); assert(equal(s,r)); This is analogous to list zippers in functional languages in the same way that input ranges are analogous to lists.
Oct 07 2015
prev sibling parent Trass3r <un known.com> writes:
Here's the original discussion with Eric's elaborate answer:
http://ericniebler.com/2014/02/21/introducing-iterables/#comment-403

 Because I want to leverage the vast amount of iterator-based 
 code already written, and because in my experience, I don’t 
 find that ranges as primitives solve all the problems that 
 iterators do.
 Many algorithms return positions. These all suffer the same 
 problem as find. One algorithm implementation isn’t sufficient; 
 you need bunches of differently-named algorithms that differ 
 only in the subrange they return.
 As for the political argument: I want ranges in the standard. 
 There is just no way the C++ standardization committee would 
 ever consider a range-only interface.
Oct 08 2015
prev sibling next sibling parent reply Kagamin <spam here.lot> writes:
On Wednesday, 7 October 2015 at 14:59:28 UTC, Trass3r wrote:
 On Tuesday, 6 October 2015 at 22:39:01 UTC, Ulrich Küttler 
 wrote:
 Yes, this is an explanation. Thanks. So the argument being C++ 
 customs. Now that you mention it, this seems to be the 
 argument in Eric's D4128 paper, too.

 I was hoping for a somewhat deeper reasoning. Out of 
 curiously, I am still trying to grasp all the implications. 
 Ranges are hard.
Another one is "odd number of iterators algorithms"
 http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4128.html#appendix-3-d-ranges-and-algorithmic-complexity
 D’s choice of algorithmic basis operations is inherently less 
 efficient than C++’s.
Hmm... conceptually a bidirectional range should be able to iterate back and forth: void is_word_boundary(Bidi r) { bool is_word_prev = r.re.empty ? false : isword(r.re.back); bool is_word_this = r.empty ? false : isword(r.front); return is_word_prev != is_word_this; } auto i = myrange; for(; !i.empty; i.popFront()) if( is_word_boundary(i) ) break;
Oct 08 2015
next sibling parent Kagamin <spam here.lot> writes:
The backward range can have an input range interface, like retro:

void is_word_boundary(Bidi r)
{
     bool is_word_prev = r.prev.empty ? false : 
isword(r.prev.front);
     bool is_word_this = r.empty ? false : isword(r.front);
     return is_word_prev != is_word_this;
}
Oct 08 2015
prev sibling parent reply John Colvin <john.loughran.colvin gmail.com> writes:
On Thursday, 8 October 2015 at 12:35:08 UTC, Kagamin wrote:
 Hmm... conceptually a bidirectional range should be able to 
 iterate back and forth:

 void is_word_boundary(Bidi r)
 {
     bool is_word_prev = r.re.empty ? false : isword(r.re.back);
     bool is_word_this = r.empty ? false : isword(r.front);
     return is_word_prev != is_word_this;
 }

 auto i = myrange;
 for(; !i.empty; i.popFront())
     if( is_word_boundary(i) )
         break;
On Thursday, 8 October 2015 at 12:53:24 UTC, Kagamin wrote:
 The backward range can have an input range interface, like 
 retro:

 void is_word_boundary(Bidi r)
 {
     bool is_word_prev = r.prev.empty ? false : 
 isword(r.prev.front);
     bool is_word_this = r.empty ? false : isword(r.front);
     return is_word_prev != is_word_this;
 }
What you're effectively describing is a trio of iterators wrapped to give an interface of two linked ranges. popFront grows the first one and shrinks the second. I'd be interested to see how to construct that, given a generic range as input.
Oct 08 2015
parent reply Kagamin <spam here.lot> writes:
On Thursday, 8 October 2015 at 13:10:24 UTC, John Colvin wrote:
 What you're effectively describing is a trio of iterators 
 wrapped to give an interface of two linked ranges. popFront 
 grows the first one and shrinks the second. I'd be interested 
 to see how to construct that, given a generic range as input.
The C++ example doesn't work with generic iterators, it needs a specific ability to iterate in both directions, hence a bidirectional range. The way ranges are used for iteration, they can be seen as adapters for iterators providing various consistent interfaces depending on their capabilities. In this example we need a bidirectional range that can go back and forth, one way to do it is to provide undo mechanism like undoPopFront and frontUndoEmpty to allow the range grow back, thus remaining a range that is a list of items and not an iterator. Another way is to provide a reverse range of previously popped items - this can be seen as iterator or not, more like a range with history rather than an undoable input range, so maybe the getter should be `history`.
Oct 08 2015
parent reply John Colvin <john.loughran.colvin gmail.com> writes:
On Thursday, 8 October 2015 at 14:36:03 UTC, Kagamin wrote:
 On Thursday, 8 October 2015 at 13:10:24 UTC, John Colvin wrote:
 What you're effectively describing is a trio of iterators 
 wrapped to give an interface of two linked ranges. popFront 
 grows the first one and shrinks the second. I'd be interested 
 to see how to construct that, given a generic range as input.
The C++ example doesn't work with generic iterators, it needs a specific ability to iterate in both directions, hence a bidirectional range.
Of course.
 The way ranges are used for iteration, they can be seen as 
 adapters for iterators providing various consistent interfaces 
 depending on their capabilities. In this example we need a 
 bidirectional range that can go back and forth, one way to do 
 it is to provide undo mechanism like undoPopFront and 
 frontUndoEmpty to allow the range grow back, thus remaining a 
 range that is a list of items and not an iterator.
I much prefer this second version:
 Another way is to provide a reverse range of previously popped 
 items - this can be seen as iterator or not, more like a range 
 with history rather than an undoable input range, so maybe the 
 getter should be `history`.
my question is: How, in practice, does one take a bidirectional range and make one of these new things? I foresee some difficulty, but perhaps I'm just not being imaginative enough.
Oct 08 2015
next sibling parent "H. S. Teoh via Digitalmars-d" <digitalmars-d puremagic.com> writes:
On Thu, Oct 08, 2015 at 02:46:05PM +0000, John Colvin via Digitalmars-d wrote:
 On Thursday, 8 October 2015 at 14:36:03 UTC, Kagamin wrote:
On Thursday, 8 October 2015 at 13:10:24 UTC, John Colvin wrote:
What you're effectively describing is a trio of iterators wrapped to
give an interface of two linked ranges. popFront grows the first one
and shrinks the second. I'd be interested to see how to construct
that, given a generic range as input.
The C++ example doesn't work with generic iterators, it needs a specific ability to iterate in both directions, hence a bidirectional range.
Of course.
The way ranges are used for iteration, they can be seen as adapters
for iterators providing various consistent interfaces depending on
their capabilities. In this example we need a bidirectional range
that can go back and forth, one way to do it is to provide undo
mechanism like undoPopFront and frontUndoEmpty to allow the range
grow back, thus remaining a range that is a list of items and not an
iterator.
I much prefer this second version:
Another way is to provide a reverse range of previously popped items
- this can be seen as iterator or not, more like a range with history
rather than an undoable input range, so maybe the getter should be
`history`.
my question is: How, in practice, does one take a bidirectional range and make one of these new things? I foresee some difficulty, but perhaps I'm just not being imaginative enough.
Bidirectional ranges do have a fundamental lack in their definition, in that the bidirectionality is weaker than the C++ form of bidirectionality. For example, suppose you're given some bidirectional range r, with swappable elements. Clearly, reverse(r) is easily implementable (just swap .front and .back, then popFront() and popBack() until the range is empty). However, suppose you want to reverse the last n elements of r. How would you do it? Conceptually speaking, if the range is bidirectional, then its last segment of n elements ought to be bidirectional too, right? However, there is currently no (easy) way to get a bidirectional subrange out of r, using the current range primitives. One brute force way to do it, is to iterate a .save'd copy of r (since bidirectionality implies forward range) from the front, until there are only n elements left, then perform the reverse() operation. However, this is horribly inefficient if n is relatively small w.r.t. the total number of elements in r. It gets worse if r does not have .length, so you may have to iterate over *two* .save'd copies of r so that you know the subrange you end up with has exactly n elements (since you can't tell how many elements are in the subrange until you reach the end). Ideally, though, we'd like to be able to iterate from the end of r, so that we only incur the cost of calling .popBack n times. However, no amount of trickery with the current bidirectional range API is going to get you this subrange by iterating from the back. The problem is that once you call .popBack n times, there's no way to turn .back into the new .front of the subrange. You can't unpop .back once you've called popBack(), so you can't implement .front on the subrange. Whereas with iterators, you *could* just do iter-- n times, then use iter with the original .end() to form the n element subrange. So D's bidirectional ranges are inherently weaker than a pair of C++ bidirectional iterators, because D's bidirectional ranges are, under the hood, a pair of *uni-directional* iterators in opposite directions. Once you advance either iterator, you can't go back anymore without resorting to ugly inefficient hacks (e.g., allocate a stack of .save'd positions), whereas in C++ both ends are bidirectional, and can go forward/back at anytime. If we were to add an .unpop primitive to bidirectional ranges, though, then we could solve this problem. However, I'm not sure how this fits in with the overall concept of ranges. T -- Век живи - век учись. А дураком помрёшь.
Oct 08 2015
prev sibling parent reply Kagamin <spam here.lot> writes:
On Thursday, 8 October 2015 at 14:46:07 UTC, John Colvin wrote:
 Another way is to provide a reverse range of previously popped 
 items - this can be seen as iterator or not, more like a range 
 with history rather than an undoable input range, so maybe the 
 getter should be `history`.
my question is: How, in practice, does one take a bidirectional range and make one of these new things? I foresee some difficulty, but perhaps I'm just not being imaginative enough.
It should be probably possible to undo the history range too, but it would be future, so it looks like there can be a better interface: beforeFront returns a normal bidirectional range of items before current front, afterBack returns a normal bidirectional range of items after back, so r.beforeFront.back is an item right before current front. This makes it more symmetric, and properties return ranges of the same type as the source range, but I don't know how to name such a range :) A range with shadows? Those ranges can be seen as shadows (before and after). Yes D's bidirectional range provides less guarantees than C++ bidirectional iterator, but you can build it on a random access range that provides more guarantees than bidirectional iterator, or you can provide a range with shadows, that provides as much guarantees as C++ bidirectional iterator, no less, no more.
Oct 08 2015
parent reply Kagamin <spam here.lot> writes:
OK, I thought a little more and... Name: divisible range. It 
occurred to me that we only need to reverse logic of 
bidirectional range: while bidirectional range is a pair of 
ranges that shrink towards each other, divisible range is divided 
into two ranges that shrink away from each other. The C++ example 
implies that begin and end must be bidirectional iterators, but 
that is not really needed as they are used for bounds checks 
only, ranges have empty for that, so the divisible range can be a 
normal input range that provides access to its left part that 
shrinks from back (backward input range?) and provides access to 
the right part.
Oct 08 2015
parent reply Timon Gehr <timon.gehr gmx.ch> writes:
On 10/08/2015 10:08 PM, Kagamin wrote:
 OK, I thought a little more and... Name: divisible range. It occurred to
 me that we only need to reverse logic of bidirectional range: while
 bidirectional range is a pair of ranges that shrink towards each other,
 divisible range is divided into two ranges that shrink away from each
 other. The C++ example implies that begin and end must be bidirectional
 iterators, but that is not really needed as they are used for bounds
 checks only, ranges have empty for that, so the divisible range can be a
 normal input range that provides access to its left part that shrinks
 from back (backward input range?) and provides access to the right part.
Isn't this the same as my suggestion? http://forum.dlang.org/post/mv3q34$bbg$1 digitalmars.com If not, what is the difference?
Oct 08 2015
next sibling parent Kagamin <spam here.lot> writes:
On Thursday, 8 October 2015 at 22:57:01 UTC, Timon Gehr wrote:
 Isn't this the same as my suggestion?
 http://forum.dlang.org/post/mv3q34$bbg$1 digitalmars.com

 If not, what is the difference?
Your range is undoable. The difference I see is that you use full (should be frontFull) and pushFront to go left, I use normal backward input range, empty and popBack - existing primitives. Also pushFront may suggest you're adding new items at the front, maybe your methods should be frontUndoEmpty and undoPopFront?
Oct 09 2015
prev sibling parent Kagamin <spam here.lot> writes:
Also imagine you want to write an algorithm that iterates 
backwards, you must choose which set of primitives to use: 
back+empty+popBack or front+frontUndoEmpty+undoPopFront, and an 
undoable bidirectional range will support both.
Oct 09 2015
prev sibling parent reply Eric Niebler <eniebler boost.org> writes:
On Wednesday, 7 October 2015 at 14:59:28 UTC, Trass3r wrote:
 On Tuesday, 6 October 2015 at 22:39:01 UTC, Ulrich Küttler  
 wrote:
 Yes, this is an explanation. Thanks. So the argument being C++ 
 customs. Now that you mention it, this seems to be the 
 argument in Eric's D4128 paper, too.

 I was hoping for a somewhat deeper reasoning. Out of 
 curiously, I am still trying to grasp all the implications. 
 Ranges are hard.
Another one is "odd number of iterators algorithms"
 http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4128.html#appendix-3-d-ranges-and-algorithmic-complexity
D’s choice of algorithmic basis operations is inherently less efficient than C++’s.
Glad that you guys found my rationale. Yes, those are the two big reasons. Trying to express algorithms without any clear abstraction of "position within range" (independent of ranges) is hard and awkward, and occasionally causes algorithms to be less efficient. IMO, James Touton's "position-based ranges"[1] was/is a viable design of a ranges-first interface that also had a (very weak but sufficient) notion of position. It might be a direction for D if you ever find it necessary. It's true that the initial version of Boost.Range wasn't terribly interesting. As early as 12/2004, I was working on a set of extensions to Boost.Range that added range adaptors that chain. (See https://svn.boost.org/svn/boost/sandbox/boost/range_ex.) Lazy range operations that compose is where range-based design starts. That's as far back as I can trace my work on "real ranges". This work was eventually merged into Boost.Range as Range v2. On Thursday, 1 October 2015 at 08:37:37 UTC, Walter Bright wrote:
 Range iteration over arrays have been around in D since the 
 beginning and a more general proposal first appears here:

 http://www.digitalmars.com/d/archives//12773.html
I don't see any generic description there of what constitutes a range or how to leverage it in user code, just a discussion of the foreach language construct.
 I found a link to Thorsten's Boost range:

 http://www.boost.org/doc/libs/1_34_0/libs/range/doc/intro.html
 http://www.boost.org/doc/libs/1_34_0/libs/range/doc/range.html

 It returns an iterator, so I don't think it is what we'd 
 consider a range to be today.

 Matthew's ranges had the following members:

     current
     advance
     is_open

 corresponding to front, popFront, and empty.

 So I'd say given what I can dig up, that D's ranges were more 
 advanced than Boost's were at the time.
Walter, you seem to suggest that Real Ranges have a popFront/front interface. Naturally by that metric C++ ranges don't count! But IMO that's not what matters. What matters is the programming model that ranges permit. Boost.Range's model where ranges are a layer over iterators can and does support that model, as my range proposal and my range_ex library from 2004 demonstrate. To be honest, this whole conversation is kind of funny to me. It reminds me of the Bugs Bunny cartoon where Marvin the Martian plants his flag on Earth and says, "I claim this planet in the name of [Digital] Mars!" We Earthlings respectfully disagree. :-) Eric [^1] http://www.open-std.org/pipermail/ranges/2014-March/000499.html
Oct 09 2015
next sibling parent reply Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
On 10/10/15 12:58 AM, Eric Niebler wrote:
 To be honest, this whole conversation is kind of funny to me. It
 reminds me of the Bugs Bunny cartoon where Marvin the Martian plants
 his flag on Earth and says, "I claim this planet in the name of
 [Digital] Mars!" We Earthlings respectfully disagree. :-)
Only it's the other way around, which makes the matter quite ironic. You wrote:
 P.S. I see lots of people here assuming that C++ is playing catch-up
 to D because D has ranges and C++ doesn't yet. That is ignoring the
 long history of ranges in C++. C++ got ranges in the form of the
 Boost.Range library by Thorsten Ottoson sometime in the early 00's.
 Andrei didn't implement D's ranges until many years after. The ranges
 idea is older than dirt. It's not a D invention.
I think it would be a bit of a stretch to describe D ranges as derivative of Boost ranges. Anyhow, it's best for us all to focus on doing good work instead of pettily fighting for irrelevant credit. Andrei
Oct 09 2015
parent reply Eric Niebler <eniebler boost.org> writes:
On Saturday, 10 October 2015 at 06:15:10 UTC, Andrei Alexandrescu 
wrote:
 On 10/10/15 12:58 AM, Eric Niebler wrote:
 To be honest, this whole conversation is kind of funny to me. 
 It
 reminds me of the Bugs Bunny cartoon where Marvin the Martian 
 plants
 his flag on Earth and says, "I claim this planet in the name of
 [Digital] Mars!" We Earthlings respectfully disagree. :-)
Only it's the other way around, which makes the matter quite ironic. You wrote:
 P.S. I see lots of people here assuming that C++ is playing 
 catch-up
 to D because D has ranges and C++ doesn't yet. That is 
 ignoring the
 long history of ranges in C++. C++ got ranges in the form of 
 the
 Boost.Range library by Thorsten Ottoson sometime in the early 
 00's.
 Andrei didn't implement D's ranges until many years after. The 
 ranges
 idea is older than dirt. It's not a D invention.
I think it would be a bit of a stretch to describe D ranges as derivative of Boost ranges.
If I implied that I believe that D ranges were based on Boost.Range, then I apologize. I don't believe that. I suspect (but don't know) that ranges in D were independently invented without knowledge of the long history of them in C++. Which is fine except for the claims that C++ is playing catch-up. It's not.
 Anyhow, it's best for us all to focus on doing good work 
 instead of pettily fighting for irrelevant credit.
I only jumped in when I saw some disparagement of C++ and my work which (IMO) was both petty and wrong. I would very much like to drop this and get back to productive work. \e
Oct 10 2015
next sibling parent "H. S. Teoh via Digitalmars-d" <digitalmars-d puremagic.com> writes:
On Sat, Oct 10, 2015 at 06:06:59PM +0000, Eric Niebler via Digitalmars-d wrote:
 On Saturday, 10 October 2015 at 06:15:10 UTC, Andrei Alexandrescu wrote:
[...]
Anyhow, it's best for us all to focus on doing good work instead of
pettily fighting for irrelevant credit.
I only jumped in when I saw some disparagement of C++ and my work which (IMO) was both petty and wrong. I would very much like to drop this and get back to productive work.
[...] Eric, if I came across as disparaging your work, I apologize, as that was never my intention. As the author of the article that you used as the basis for your presentation, I am very honored to have you acknowledge my work in the C++ community. My comment about C++ playing catchup wasn't intended to be petty disparagement either, it's a reflection of my consideration that C++ has been heading in the wrong direction (IMO), and only now is "turning the ship", so to speak, toward where other languages have already gone ahead. I'm a C++ programmer myself, and for many years have faced many problems and issues that arose from certain design decisions in C++. After discovering D and realizing that I don't *need* to deal with such issues after all, because D made different design decisions, only to learn later on that C++ is now also trying to head in the same directions, it's a bit hard not to perceive C++ as playing catch-up. T -- Gone Chopin. Bach in a minuet.
Oct 10 2015
prev sibling next sibling parent reply Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
On 10/10/15 9:06 PM, Eric Niebler wrote:
 On Saturday, 10 October 2015 at 06:15:10 UTC, Andrei Alexandrescu wrote:
 On 10/10/15 12:58 AM, Eric Niebler wrote:
 To be honest, this whole conversation is kind of funny to me. It
 reminds me of the Bugs Bunny cartoon where Marvin the Martian plants
 his flag on Earth and says, "I claim this planet in the name of
 [Digital] Mars!" We Earthlings respectfully disagree. :-)
Only it's the other way around, which makes the matter quite ironic. You wrote:
 P.S. I see lots of people here assuming that C++ is playing catch-up
 to D because D has ranges and C++ doesn't yet. That is ignoring the
 long history of ranges in C++. C++ got ranges in the form of the
 Boost.Range library by Thorsten Ottoson sometime in the early 00's.
 Andrei didn't implement D's ranges until many years after. The ranges
 idea is older than dirt. It's not a D invention.
I think it would be a bit of a stretch to describe D ranges as derivative of Boost ranges.
If I implied that I believe that D ranges were based on Boost.Range, then I apologize. I don't believe that.
Well the simple fact is then that P.S. has done an awful job at conveying your point.
 I suspect (but don't know) that
 ranges in D were independently invented without knowledge of the long
 history of them in C++.
Well that's easy to figure. "Iterators Must Go" at https://archive.org/details/AndreiAlexandrescuKeynoteBoostcon2009 starting around minute 1:01:50 mentions "Ranges are not Boost ranges. They're very different". Same talk at 1:02:34 describes how Boost and Adobe defined their own ranges ("Boost and Adobe did make an interesting step in a good direction, however things must be taken way further than that." So there was knowledge of said long history of ranges in C++. Far as I can tell "Iterators Must Go" was immediately and universally recognized as a turning point in how people approached getting work done using ranges. (Existing work I only found out recently: Matthew Wilson did define ranges as a generalization of D slices; his work was not based on C++ idioms, and made no inroads in the C++ community. His work _is_ strongly related to today's D ranges, I ought to have found that, and it is my mistake to not have.)
 Which is fine except for the claims that C++ is
 playing catch-up. It's not.

 Anyhow, it's best for us all to focus on doing good work instead of
 pettily fighting for irrelevant credit.
I only jumped in when I saw some disparagement of C++ and my work which (IMO) was both petty and wrong. I would very much like to drop this and get back to productive work.
Eric, I don't know about others but I respect and like your work. I appreciate its originality, too. What I see here is a simple case when someone said something wrong and got his behind appropriately handed on a dish constructed of a precious metal. Andrei
Oct 10 2015
parent reply Ola Fosheim =?UTF-8?B?R3LDuHN0YWQ=?= writes:
On Saturday, 10 October 2015 at 22:06:31 UTC, Andrei Alexandrescu 
wrote:
 So there was knowledge of said long history of ranges in C++. 
 Far as I can tell >"Iterators Must Go" was immediately and 
 universally recognized as a turning point in >how people 
 approached getting work done using ranges.
You've already published the background for your library approach here: http://www.informit.com/articles/article.aspx?p=1407357&seqNum=4 Which basically states the foundation: GoF iterators + STL. So you've already killed the novelty game yourself. GoF patterns is just an attempt to describe _common_ patterns in software design. Stepanov "C++ pointer-iterators" was an attempt to break away from the heavier GoF iterators (which D calls ranges) with something more lightweight. If one tries to enumerate all kinds of types of iterators one will end up with a combinatorial explosion, so much for generality. Stepanovs approach was probably also an attempt to get away from this combinatorial explosion by providing pointer-semantics instead. One of the most important and convenient iterators (which C++ fails to deliver) are what GoF calls "roboust iterators": iterators that allow deletions. To get there safely and conveniently iterators have to be made a language feature, since it requires static analysis in the general case, IMO. Want to innovate? Provide language support.
Oct 12 2015
parent reply Kagamin <spam here.lot> writes:
On Monday, 12 October 2015 at 07:08:19 UTC, Ola Fosheim Grøstad 
wrote:
 One of the most important and convenient iterators (which C++ 
 fails to deliver) are what GoF calls "roboust iterators": 
 iterators that allow deletions. To get there safely and 
 conveniently iterators have to be made a language feature, 
 since it requires static analysis in the general case, IMO.

 Want to innovate? Provide language support.
http://forum.dlang.org/post/hmtj0e$1qmg$1 digitalmars.com
Oct 12 2015
parent Ola Fosheim =?UTF-8?B?R3LDuHN0YWQ=?= writes:
On Monday, 12 October 2015 at 12:29:28 UTC, Kagamin wrote:
 http://forum.dlang.org/post/hmtj0e$1qmg$1 digitalmars.com
Meh, library solutions are no good. Insertions and deletions mess up many things that effects performance, including vectorisation.
Oct 12 2015
prev sibling parent deadalnix <deadalnix gmail.com> writes:
On Saturday, 10 October 2015 at 18:07:02 UTC, Eric Niebler wrote:
 If I implied that I believe that D ranges were based on 
 Boost.Range, then I apologize. I don't believe that. I suspect 
 (but don't know) that ranges in D were independently invented 
 without knowledge of the long history of them in C++. Which is 
 fine except for the claims that C++ is playing catch-up. It's 
 not.
Ho come on, that's pretty obvious that C++ is playing catch up with all the new goodies there are in modern programming languages (which includes D, but not only). There is nothing wrong with it. This is why the dev cycle went from eternity between 2 versions to few years. The talking point of the C++ inner circle has been super weird to say the least. It is like admitting it would be a supreme shame, while it is in fact the sign of a community that which to bring the best to its users, something nobody should be ashamed of.
 Anyhow, it's best for us all to focus on doing good work 
 instead of pettily fighting for irrelevant credit.
I only jumped in when I saw some disparagement of C++ and my work which (IMO) was both petty and wrong. I would very much like to drop this and get back to productive work. \e
This is where you get it wrong. Looking at what others are doing and adopting the good ideas is the characteristic of a language community that is focused on improving the language rather than participating in some ego battle. There was no disparagement of your work as far as I can tell. The fact you choose to take it that way is what elicit this conversation in the first place.
Oct 10 2015
prev sibling parent reply Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
On 10/10/15 12:58 AM, Eric Niebler wrote:
 Trying to express algorithms without any clear abstraction of "position
 within range" (independent of ranges) is hard and awkward, and
 occasionally causes algorithms to be less efficient.
I agree that ranges are a weaker basis than iterators. But it's not necessarily that a notion of position is the only way out. Ranges can be made as strong a basis by adding the O(1) primitives r1.before(r2) and r1.after(r2) that return the prefix/suffix following r2 within r1. With those I hope to be able to show easily that algorithms needing "iterator in the middle" can be redone. I think I need to sit down and define these primitives (albeit they aren't used that frequently) and use them in a few fundamental algorithms to just close the matter once and for all. Andrei
Oct 09 2015
parent "H. S. Teoh via Digitalmars-d" <digitalmars-d puremagic.com> writes:
On Sat, Oct 10, 2015 at 09:52:22AM +0300, Andrei Alexandrescu via Digitalmars-d
wrote:
 On 10/10/15 12:58 AM, Eric Niebler wrote:
Trying to express algorithms without any clear abstraction of
"position within range" (independent of ranges) is hard and awkward,
and occasionally causes algorithms to be less efficient.
I agree that ranges are a weaker basis than iterators. But it's not necessarily that a notion of position is the only way out. Ranges can be made as strong a basis by adding the O(1) primitives r1.before(r2) and r1.after(r2) that return the prefix/suffix following r2 within r1. With those I hope to be able to show easily that algorithms needing "iterator in the middle" can be redone.
I assume .before would be implemented in a specialization of forward ranges, and .after in a specialization of bidirectional ranges?
 I think I need to sit down and define these primitives (albeit they
 aren't used that frequently) and use them in a few fundamental
 algorithms to just close the matter once and for all.
[...] It would also fix the current bug in nextPermutation that claims that it supports bidirectional ranges, when in fact it requires random access ranges, precisely because reversing the last n elements requires the "iterator in the middle" construct. T -- Gone Chopin. Bach in a minuet.
Oct 10 2015
prev sibling parent Walter Bright <newshound2 digitalmars.com> writes:
On 10/5/2015 7:31 PM, Eric Niebler wrote:
 The design of the D ranges and algorithms owe quite a lot to C++, and I've
heard
 Andrei say as much.
D ranges owe plenty to C++ iterators and algorithms, no doubt. Boost ranges, I can't agree.
 Stepanov did the hard work of defining common algorithms in
 terms of iterators of different strength. Given that starting point, ranges of
 different strength are an "obvious" next step that many people thought up
 independently. D took it one way and C++ went another.
It seems obvious in retrospect, I agree. But looking at the early Boost ranges, they didn't take the obvious step :-)
 When designing my range library, I looked at all the prior art available to me
 including D ranges and decided D's path was not the right one for C++. My work
 is based on Boost.Range. I only posted here to clear up what appeared to me to
 be confusion about that.
Oct 06 2015
prev sibling next sibling parent lobo <swamplobo gmail.com> writes:
On Thursday, 1 October 2015 at 05:47:25 UTC, Eric Niebler wrote:

...[snip]...
 Hope that clears things up.
It does, thank you.
 Eric

 P.S. I see lots of people here assuming that C++ is playing 
 catch-up to D because D has ranges and C++ doesn't yet. That is 
 ignoring the long history of ranges in C++. C++ got ranges in 
 the form of the Boost.Range library by Thorsten Ottoson 
 sometime in the early 00's. Andrei didn't implement D's ranges 
 until many years after. The ranges idea is older than dirt. 
 It's not a D invention.
Fair point, I did overlook boost.range when considering the C++ range options. bye lobo
Oct 01 2015
prev sibling parent bitwise <bitwise.pvt gmail.com> writes:
On Thursday, 1 October 2015 at 05:47:25 UTC, Eric Niebler wrote:
 On Thursday, 1 October 2015 at 04:08:00 UTC, bitwise wrote:
 I understand, but the C++ committee seems very conservative to 
 me, so when it's this easy to add for(:) support by giving 
 ranges begin()/end() functions, it makes me doubt they will 
 actually change the language for it.
As of C++11, C++ has the for(auto e:range) control structure you are looking for. I would be using it here except for one thing: in my proposal, begin() and end() don't have to return objects of the same type! begin() must return an iterator and end() must return something that is EqualityComparable with the iterator -- but it doesn't have to be an iterator. That makes many types of iterators vastly simpler to implement and more efficient at runtime. C++'s built-in range-based for(:) loop expects begin() and end() to return objects of the same type. The committee is already talking about loosening that constraint so that the ranges I'm proposing Just Work with the existing built-in looping construct. Until then, there is an ugly macro. It's a temporary hack, nothing more.
Did you look at my example(this one is updated)? http://ideone.com/X1JAEn I've factored out a 'range_iterator' in this version. I would probably rethink the way I've done the chaining, but there is nothing complicated about adding foreach support as I've implemented it in my example. From the callers point of view, it's a typedef and two functions. I really doubt anything could be done that would offer a perceptible performance gain over what I've done in my example. I suppose it's a moot point if C++ is actually planning native range support. Bit
Oct 01 2015
prev sibling parent reply Manu via Digitalmars-d <digitalmars-d puremagic.com> writes:
On 1 October 2015 at 08:47, H. S. Teoh via Digitalmars-d
<digitalmars-d puremagic.com> wrote:
 [...]
 (D has seriously ruined my life; I simply can't bring myself to go back to C++
anymore. At least not voluntarily.)
OMG, this! Seriously, this is more true than I can express in words ;) My career is severely damaged by D, because I can't use D at work (no matter how hard I try, for however many years), and I can't enjoy coding C++ anymore! >_<
 Also, this seems to confirm that C++ is gradually falling to the
 position where it's playing catch-up with respect to innovations in
 newer languages like D and Rust. The fact that ranges are being proposed
 for the C++ standard library is a big endorsement of D, IMO.
My strategy has been to backport D ideas into C++ over the past year since my last failed attempt to get D into my office, and this has been an AGONISING and extremely time consuming process. I have slices, ranges (as best I can), delegates, and my code is generally D-ish. Most people in the office like working with it, and they're starting to realise the connection to D ;) None of it would be possible without C++11 variadic templates. It's been the biggest improvement to C++ for a long time, even though some of the constructs they lead to are far more obtuse than anything I've ever seen emerge in C++ before.
Oct 03 2015
parent Ola Fosheim =?UTF-8?B?R3LDuHN0YWQ=?= writes:
On Saturday, 3 October 2015 at 08:58:26 UTC, Manu wrote:
 My strategy has been to backport D ideas into C++ over the past 
 year
 since my last failed attempt to get D into my office, and this 
 has
 been an AGONISING and extremely time consuming process.
 I have slices, ranges (as best I can), delegates, and my code is
 generally D-ish.
What do you need delegates for when you have flexible function-object lambdas? Microsoft GSL have array_view for slicing and transferring views of arrays/memory to functions. It supports fixed sized slices (so you don't transfer length) and multi dimensional slices). A bit rough, but usable: https://github.com/Microsoft/GSL/blob/master/tests/array_view_tests.cpp
Oct 05 2015
prev sibling next sibling parent reply =?UTF-8?Q?Ali_=c3=87ehreli?= <acehreli yahoo.com> writes:
On 09/29/2015 06:45 PM, deadalnix wrote:
 https://www.youtube.com/watch?v=mFUXNMfaciE

 From
 http://wiki.dlang.org/Component_programming_with_ranges

 Congrat H. S. Teoh
Yay! :) I almost gave the same talk! This talk could have been a part of DConf 2014 if H. S. Teoh or I could go to the conference. Here is an email exchange between us in January 2014: Ali -- "I wanted to let you know that your article "Component programming with ranges" would be an excellent topic for DConf 2014 and I would love to hear it from you. :) In case you are presenting something else or simply cannot make it to the conference, I would like to propose the same topic for DConf 2014. (But I am sure you and others have done the same already. :) )" H. S. Teoh -- "please feel free to propose this topic; it would be nice (for me!) to hear it from somebody else's viewpoint! ;-)" Ali
Sep 30 2015
parent =?UTF-8?Q?Ali_=c3=87ehreli?= <acehreli yahoo.com> writes:
On 09/30/2015 08:02 AM, Ali Çehreli wrote:

 if H. S. Teoh or I could go to the conference.
Oops! I've mixed up the years. I did go to DConf 2014 but not DConf 2015. Still... :) Ali
Sep 30 2015
prev sibling next sibling parent reply Joakim <dlang joakim.fea.st> writes:
On Wednesday, 30 September 2015 at 01:45:49 UTC, deadalnix wrote:
 https://www.youtube.com/watch?v=mFUXNMfaciE

 From
 http://wiki.dlang.org/Component_programming_with_ranges

 Congrat H. S. Teoh
Thanks for the link, I watched the whole video today and it was a very good presentation by Niebler. He mentions D and Teoh's example right at the top and gets an ovation at the 49 minute-mark, once he's gone through his entire C++ version of Teoh's D example. Interesting that they're using the pipe symbol for chaining, more explicitly mimicking the unix command line. The fact that scoping meant that views and actions were explicitly labeled could be a nice benefit, though I generally dislike such verbosity normally. It is amazing how noisy some of the implementation code with templates is in C++: I felt like I was looking at some Haskell variant compared to how clean D would look for the same code.
Sep 30 2015
next sibling parent reply wobbles <grogan.colin gmail.com> writes:
On Wednesday, 30 September 2015 at 16:06:59 UTC, Joakim wrote:
 On Wednesday, 30 September 2015 at 01:45:49 UTC, deadalnix 
 wrote:
 https://www.youtube.com/watch?v=mFUXNMfaciE

 From
 http://wiki.dlang.org/Component_programming_with_ranges

 Congrat H. S. Teoh
Thanks for the link, I watched the whole video today and it was a very good presentation by Niebler. He mentions D and Teoh's example right at the top and gets an ovation at the 49 minute-mark, once he's gone through his entire C++ version of Teoh's D example. Interesting that they're using the pipe symbol for chaining, more explicitly mimicking the unix command line. The fact that scoping meant that views and actions were explicitly labeled could be a nice benefit, though I generally dislike such verbosity normally. It is amazing how noisy some of the implementation code with templates is in C++: I felt like I was looking at some Haskell variant compared to how clean D would look for the same code.
Another thing I noticed that showed D nice-ness is when he was converting the weeks ranges to a string, the flow of the functions went from the bottom up (he specifically said "start from the bottom"). It looks so weird to me after using UFCS for so long.
Sep 30 2015
parent Brad Roberts via Digitalmars-d <digitalmars-d puremagic.com> writes:
On 9/30/15 12:12 PM, wobbles via Digitalmars-d wrote:
 On Wednesday, 30 September 2015 at 16:06:59 UTC, Joakim wrote:
 On Wednesday, 30 September 2015 at 01:45:49 UTC, deadalnix wrote:
 https://www.youtube.com/watch?v=mFUXNMfaciE

 From
 http://wiki.dlang.org/Component_programming_with_ranges

 Congrat H. S. Teoh
Thanks for the link, I watched the whole video today and it was a very good presentation by Niebler. He mentions D and Teoh's example right at the top and gets an ovation at the 49 minute-mark, once he's gone through his entire C++ version of Teoh's D example. Interesting that they're using the pipe symbol for chaining, more explicitly mimicking the unix command line. The fact that scoping meant that views and actions were explicitly labeled could be a nice benefit, though I generally dislike such verbosity normally. It is amazing how noisy some of the implementation code with templates is in C++: I felt like I was looking at some Haskell variant compared to how clean D would look for the same code.
Another thing I noticed that showed D nice-ness is when he was converting the weeks ranges to a string, the flow of the functions went from the bottom up (he specifically said "start from the bottom"). It looks so weird to me after using UFCS for so long.
The 'start from the bottom' part of that part of the code was because he wanted to talk about it in that order. The logic in the code flowed in exactly the order you'd expect it to: leading padding bytes first followed by formatted days.
Sep 30 2015
prev sibling parent Timon Gehr <timon.gehr gmx.ch> writes:
On 09/30/2015 06:06 PM, Joakim wrote:
 It is amazing how noisy some of the implementation code with templates
 is in C++: I felt like I was looking at some Haskell variant compared to
 how clean D would look for the same code.
It's easy to write a clean Haskell version, in case you were trying to imply otherwise.
Oct 01 2015
prev sibling next sibling parent Jim Hewes <jimhewes gmail.com> writes:
I haven't watched it yet, but it seems to be similar to this one from 
NWCPP I watched recently:

https://www.youtube.com/watch?v=8yV2ONeWXyI
Sep 30 2015
prev sibling parent rsw0x <anonymous anonymous.com> writes:
On Wednesday, 30 September 2015 at 01:45:49 UTC, deadalnix wrote:
 https://www.youtube.com/watch?v=mFUXNMfaciE

 From
 http://wiki.dlang.org/Component_programming_with_ranges

 Congrat H. S. Teoh
D's ranges are inarguably the best part of the language and one of the major reasons to use it despite its shortcomings.
Sep 30 2015