digitalmars.D - On the richness of C++
- Georg Wrede (15/15) Apr 10 2008 I read
- Jason House (3/21) Apr 10 2008 Great question. Do we allow as much helper code in the background that ...
- Sean Kelly (29/44) Apr 10 2008 I think one could argue that the current implementation of mixins is a
- Jason House (2/13) Apr 10 2008 What's ADL? A quick web search didn't turn up any obvious definitions.....
- Sean Kelly (3/16) Apr 10 2008 Argument-dependent lookup--also called Koenig lookup.
- Kevin Bealer (42/62) Apr 10 2008 Sometimes. If you want to wrap a small type like int or char in a struc...
- Sean Kelly (29/35) Apr 10 2008 I'd personally like for "placement new" to be supported by the language....
- Kevin Bealer (10/21) Apr 10 2008 ...
- Robert Fraser (3/31) Apr 10 2008 (2) is solved in D by using scope classes. But the others still remain
- Sean Kelly (4/5) Apr 11 2008 Constructing D objects in shared memory. That's also an underlying
- Frits van Bommel (11/20) Apr 11 2008 Might I suggest that if you ever again get the urge to add placement
- Frits van Bommel (4/20) Apr 11 2008 Oh, and after reading the spec: the 'void*' in front of 'new' shouldn't
- Frits van Bommel (7/12) Apr 11 2008 Actually, that doesn't apply to class allocators. Since no instance
- Sean Kelly (9/21) Apr 11 2008 That's a slightly odd rule. I'd think that explicitly calling obj.new()...
- Sean Kelly (8/28) Apr 11 2008 Bah... forget everything I said. You're right of course. Someday I'll ...
- Robert Fraser (2/5) Apr 11 2008 Aren't "super" calls bound at compile-time?
- Sean Kelly (9/14) Apr 11 2008 My guess would be that a "super" call rebinds to the superclass' vtbl.
- Walter Bright (3/5) Apr 11 2008 I agree, they are geniuses. But that's really what is wrong with C++,
- Edward Diener (10/17) Apr 12 2008 Are D's templates a complete replacement in functionality for Boost's
- Sean Kelly (7/24) Apr 12 2008 I'm not sure if it helps, but the D book that I and some of the other
- Walter Bright (7/25) Apr 12 2008 I don't really understand Boost MPL, but D's template system is
- Edward Diener (30/49) Apr 12 2008 I do not know the MPL either although I understand the general concept.
- Georg Wrede (4/67) Apr 13 2008 Yes! And I think those are things that very may, who don't regularly
- Edward Diener (25/95) Apr 13 2008 In Boost there is an entire metaprogramming paradigm based on a set of
- Bill Baxter (29/128) Apr 13 2008 It would be interesting to see what it takes to reproduce MPL in D.
- Bill Baxter (25/162) Apr 13 2008 The ConstList will look something like
- Edward Diener (27/196) Apr 14 2008 I will look into the D libraries more, especially the ones you mention.
- Bill Baxter (12/20) Apr 14 2008 Hah, I think the same thing every time I'm forced to try to use a boost
- Edward Diener (44/70) Apr 14 2008 That is a little unfair as you are comparing documentation about a
- Lars Ivar Igesund (7/24) Apr 14 2008 "Learn to Tango with D" is definately more about D than about Tango.
- Walter Bright (8/16) Apr 15 2008 One aspect of C++ templates is rendered completely irrelevant in D is
- Edward Diener (15/34) Apr 15 2008 I assume the first means function execution which produces a constant
- Walter Bright (9/34) Apr 15 2008 C++0x has a "constexpr" proposal, which is a small subset of D's compile...
- Don Clugston (6/44) Apr 15 2008 It's fundamental. AFAIK, C++ gains its Turing-completeness purely from t...
- Walter Bright (14/38) Apr 15 2008 Yes. See std.algorithms, for one. It is written by Andrei Alexandrescu,
- Jason House (6/27) Apr 15 2008 Would you be willing to add it on dsource, scrapple, etc...? I think th...
- Walter Bright (7/45) Apr 15 2008 If you want to write such a page, I'm sure Andrei would be willing to
- Jason House (11/51) Apr 15 2008 That'd be a nice exercise in learning to stress D :) I'm assuming Andre...
- Walter Bright (4/31) Apr 15 2008 No, the point isn't clear. Closures can handle multiple threads
- Jason House (14/32) Apr 15 2008 I probably should not have rushed to make an example before running out ...
- Walter Bright (9/22) Apr 15 2008 This is just the usual distinction between value and reference
- Jason House (2/26) Apr 16 2008 The only thing I'm contesting is your statement that closures eliminate ...
- MatBec (37/38) Apr 16 2008 Instead of call some strange bind function just create a closure taking ...
- Bill Baxter (39/104) Apr 16 2008 Here's the D version for comparison:
- Jason House (3/14) Apr 16 2008 All your examples as written are problem free in D as well. Your exampl...
- Leandro Lucarella (18/36) Apr 21 2008 This is called partial function application[1] in Python, which includes
- Bruno Medeiros (20/37) Apr 25 2008 This way:
- Edward Diener (14/59) Apr 15 2008 It is only a big deal in the sense that proving a single callback
- Bill Baxter (10/29) Apr 15 2008 I think all that's needed is a way to automatically promote a function
- Edward Diener (5/38) Apr 16 2008 I totally agree with what you say here. When a D non-member function can...
- Walter Bright (3/16) Apr 15 2008 There's no reason you cannot write a template in D to do it - Andrei has...
- Sean Kelly (5/21) Apr 15 2008 Sure, but templates don't suit every situation. It's not uncommon for
- Walter Bright (4/7) Apr 16 2008 The only way to merge function pointers with delegates is to have the
- Janice Caron (6/9) Apr 16 2008 I think that all that is being suggested is that function (that which
- Sean Kelly (9/17) Apr 16 2008 I think the problem is that functions and delegates are called different...
- Sean Kelly (5/21) Apr 16 2008 Er... forget that. A D function would obviously expect its first argume...
- Bill Baxter (4/25) Apr 16 2008 Hmm. Someone wrote a long post about this long ago and claimed to have
- Kevin Bealer (21/45) Apr 16 2008 I'm not much of an ASM guru, but I would think that this could be done b...
- Bruno Medeiros (7/23) Apr 27 2008 Well, if that doesn't work, there is nothing preventing the *changing*
- Janice Caron (1/4) Apr 27 2008 This is /not/ a quote from me. This is a quote from Sean Kelly.
- Sean Kelly (6/31) Apr 27 2008 Well... I suppose the D ABI could state that if a function has a context...
- Sean Kelly (18/25) Apr 16 2008 Certainly. Templates are always faster. But they don't always suit. T...
- Bill Baxter (4/29) Apr 16 2008 Example #2 is that you might want a virtual function that accepts a
- Edward Diener (12/20) Apr 16 2008 The template approach means that one has to write a template for each
- Tomas Lindquist Olsen (6/14) Apr 18 2008 I was reading about these a few days ago, as LLVM has support for these....
- Bill Baxter (10/26) Apr 18 2008 So you mean if one uses GDC, then all calls to nested functions are
- Edward Diener (37/89) Apr 15 2008 I know of Andrei and his book. The Boost MPL superceded what he had
- Walter Bright (3/4) Apr 15 2008 I don't wish to put words in Andrei's mouth, except to say that we are
-
Edward Diener
(4/9)
Apr 15 2008
I was largely joking, via the
. I am aware of Andrei butting heads - Georg Wrede (19/48) Apr 13 2008 [my bold above]
- Bill Baxter (8/28) Apr 10 2008 Structs would be my vote for the area where C++ is more flexible and
- Craig Black (9/17) Apr 11 2008 Agree on all points. Overall, D is much more elegant and expressive tha...
- Kevin Bealer (15/23) Apr 11 2008 I wondered about this myself -- at one point I sat down and designed a b...
- Sean Kelly (17/32) Apr 11 2008 It's a bit tricky, but so long as you map the file at the same address i...
- bearophile (2/2) Apr 15 2008 I can't follow the newsgroup now, but I'd really like to know if you can...
- Janice Caron (3/4) Apr 15 2008 Given that D templates are way, way, /way/ more powerful than C++
- Bill Baxter (13/18) Apr 15 2008 The fact that D structs are way way /way/ more wimpy than C++ structs. :...
- Don Clugston (7/25) Apr 15 2008 I think it's reasonable -- boost is increasingly looking like a standard...
- Sean Kelly (10/15) Apr 15 2008 helpful for a C++ programmer; yet it gives less detail on the interestin...
- Jesse Phillips (6/31) Apr 15 2008 I would like to compliment that effort, as it is IMO that the book was
I read http://www.nwcpp.org/Downloads/2007/redcode_-_updated.pdf and upon reading it I got thinking of something else. Those familiar with C++ (aren't we all?) probably sometimes come across things that somebody has done in C++ that are simply stunning. Things that one would have thought would need a new language, or maybe just be impossible to implement at all. I know I have. (A lot of Boost stuff is like that, originally the STL got me breathless, but there's a lot that's not template related, too.) Is it just paranoia, or is C++ still more flexible and expressive than D? Are there still things you can do in C++ that are impossible or too awkward to do in D? Of course, I don't mean Obfuscated C(++). While that definitely demonstrates the unfathomable agility of the language, I'm only talking about serious, non-juvenile stuff.
Apr 10 2008
Georg Wrede Wrote:I read http://www.nwcpp.org/Downloads/2007/redcode_-_updated.pdf and upon reading it I got thinking of something else. Those familiar with C++ (aren't we all?) probably sometimes come across things that somebody has done in C++ that are simply stunning. Things that one would have thought would need a new language, or maybe just be impossible to implement at all. I know I have. (A lot of Boost stuff is like that, originally the STL got me breathless, but there's a lot that's not template related, too.) Is it just paranoia, or is C++ still more flexible and expressive than D?While I don't know how I'd really implement this in C++ or D without third-party libraries, this appears to be nothing more than tuple manipulation. If you can search for a given type in a tuple and delete a type in a tuple, then you can do this in D. I suspect that is not a significant burden for those who practice MP.Are there still things you can do in C++ that are impossible or too awkward to do in D?Great question. Do we allow as much helper code in the background that C++ users use? The paper relies on MPL (on top of TMP). MPL isn't a small little bit of C++ code either...Of course, I don't mean Obfuscated C(++). While that definitely demonstrates the unfathomable agility of the language, I'm only talking about serious, non-juvenile stuff.
Apr 10 2008
== Quote from Georg Wrede (georg nospam.org)'s articleI read http://www.nwcpp.org/Downloads/2007/redcode_-_updated.pdf and upon reading it I got thinking of something else. Those familiar with C++ (aren't we all?) probably sometimes come across things that somebody has done in C++ that are simply stunning. Things that one would have thought would need a new language, or maybe just be impossible to implement at all. I know I have. (A lot of Boost stuff is like that, originally the STL got me breathless, but there's a lot that's not template related, too.) Is it just paranoia, or is C++ still more flexible and expressive than D? Are there still things you can do in C++ that are impossible or too awkward to do in D?I think one could argue that the current implementation of mixins is a weak replacement for multiple inheritance, and that this makes certain design patterns a bit less pleasant in D than they would be in C++. Also, the lack of ADL in D can be frustrating at times, though D 2.0's overload groups may address this issue. In fact, it's overload groups and struct ctors that has me wanting to move to D 2.0.Of course, I don't mean Obfuscated C(++). While that definitely demonstrates the unfathomable agility of the language, I'm only talking about serious, non-juvenile stuff.As far a template metaprogramming is concerned, while a great deal is possible in C++ (as Boost shows), the syntax is such that I don't actually support the idea of using it for anything sufficiently non-trivial. While I feel that metaprogramming is conceptually very straightforward, actually using it to the degree suggested in modern literature tends to render the resulting program incomprehensible and unmaintainable by the vast bulk of C++ programmers. Thus I feel the issue often isn't implementing something fancy so much as making it sufficiently elegant that it's practically usable. Another issue with template metaprogramming is that there is precious little literature on the topic. Andrei's book uses it a great deal, but the only C++ book I know of that actually describes common constructs is "Generative Programming," which few people seem to have read. I'll admit that this was one motivating factor for my covering it in our book on D--I was hoping to make template metaprogramming seem a bit more understandable and at the same time show how much cleaner the D syntax is for this sort of thing. It's perhaps worth mentioning as well that between string mixins and CTFE, D is light years ahead of C++ in terms of metaprogramming. This is one area where it's fairly easy to render code completely impenetrable, but it can be quite elegant if used correctly. And CTFE is a good companion for template metaprogramming in that each have their respective strengths. Sean
Apr 10 2008
Sean Kelly Wrote:== Quote from Georg Wrede (georg nospam.org)'s articleWhat's ADL? A quick web search didn't turn up any obvious definitions...Is it just paranoia, or is C++ still more flexible and expressive than D? Are there still things you can do in C++ that are impossible or too awkward to do in D?I think one could argue that the current implementation of mixins is a weak replacement for multiple inheritance, and that this makes certain design patterns a bit less pleasant in D than they would be in C++. Also, the lack of ADL in D can be frustrating at times, though D 2.0's overload groups may address this issue. In fact, it's overload groups and struct ctors that has me wanting to move to D 2.0.
Apr 10 2008
== Quote from Jason House (jason.james.house gmail.com)'s articleSean Kelly Wrote:Argument-dependent lookup--also called Koenig lookup. Sean== Quote from Georg Wrede (georg nospam.org)'s articleWhat's ADL? A quick web search didn't turn up any obvious definitions...Is it just paranoia, or is C++ still more flexible and expressive than D? Are there still things you can do in C++ that are impossible or too awkward to do in D?I think one could argue that the current implementation of mixins is a weak replacement for multiple inheritance, and that this makes certain design patterns a bit less pleasant in D than they would be in C++. Also, the lack of ADL in D can be frustrating at times, though D 2.0's overload groups may address this issue. In fact, it's overload groups and struct ctors that has me wanting to move to D 2.0.
Apr 10 2008
Georg Wrede Wrote:I read http://www.nwcpp.org/Downloads/2007/redcode_-_updated.pdf and upon reading it I got thinking of something else. Those familiar with C++ (aren't we all?) probably sometimes come across things that somebody has done in C++ that are simply stunning. Things that one would have thought would need a new language, or maybe just be impossible to implement at all. I know I have. (A lot of Boost stuff is like that, originally the STL got me breathless, but there's a lot that's not template related, too.) Is it just paranoia, or is C++ still more flexible and expressive than D? Are there still things you can do in C++ that are impossible or too awkward to do in D? Of course, I don't mean Obfuscated C(++). While that definitely demonstrates the unfathomable agility of the language, I'm only talking about serious, non-juvenile stuff.Sometimes. If you want to wrap a small type like int or char in a structure and do really advanced class-based stuff, I think C++ lets you do this and keep both maximum efficiently and maximum flexibility, whereas in D, you need to pick either a class or a struct, and some capabilities drop out with the struct types. In C++ you can inherit a bunch of small (e.g. 4 byte) objects from each other and use template specialization to do compile time "dispatches" on the inheritance hierarchy and so on. D can do some of this but its hard to do it the same way. If you want to do really specific things with memory, C++ lets you do this, but in D classes can only be handled by their object references. You can't do a "placement new" or anything like it with D classes. In C++ you could build classes that automatically allocate themself in a shared memory segment, but in D, probably not. Note that in practice, this is hard to do right and I think is rarely used for much. But I think D's advantages far outweigh these kinds of issues for almost all real programming, and some things that are "in the pipe" like struct constructors or destructors (which one was it?) will provide some of the missing functionality. Another thing, though ... I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses. But it worries me that when first seeing it done, I can't even guess how it is possible. It also breaks down in a dozen ways -- if the expressions aren't written exactly right, the wrong things happen at compile versus runtime, binding doesn't happen right, etc. It's hard to know, until the code is running, whether it is doing anything like what you meant it to. It's sort of like a lawnmower that runs on dynamite. Programming is like a chess game -- how much you can accomplish is dependant on how many moves you can see ahead. The C++ syntax to do metaprogramming is very obscure -- this is why people didn't know it existed until after templates were invented. The fact that lambdas are possible is cool. The fact that the space of possible techniques is so opaque is less cool... in C++ you don't know if a thing is possible nearly as easily as in a language like D where the path is better marked, and where there are explicit syntaxes for these things. For example, in C++ I was trying to write a static assert, but there are several ways to do it and some of the syntaxes that used to work (arrays with 0 or even negative size) no longer counted as errors. It took a good hour working out what fails and works in what contexts. And I still only know the answer for one compiler. (I think there's a better version in Imperfect C++ for those interested). In D, the syntax is simpler, and more direct, and more explicit, so you don't need to be a chess master (as often) to figure out whether you can even get from point A to point B, or how to get there, (or why it won't compile...) Kevin
Apr 10 2008
== Quote from Kevin Bealer (kevinbealer gmail.com)'s articleIf you want to do really specific things with memory, C++ lets you do this, but in D classes can only be handled by their object references. You can't do a "placement new" or anything like it with D classes. In C++ you could build classes that automatically allocate themself in a shared memory segment, but in D, probably not. Note that in practice, this is hard to do right and I think is rarely used for much.I'd personally like for "placement new" to be supported by the language. I've considered adding a new(void*) method to Object for this purpose in Tango, but haven't experimented enough to find out if this would cause any problems. One I can think of is that certain hierarchies seem like they could cause this to throw: class Object { void* new( size_t s, void* p ) { return p; } } class C { void* new( size_t s, Allocator a ) { return a.alloc( s ); } } class D { void* new( size_t s, Allocator a ) { printf( "hello!\n" ); return super.new( s, a ); } void* pos = ...; auto var = new( pos ) D; With the vtbl checking in D, I think the above call will throw a "not implemented" message because D overrides one inherited "new" routine but not the "placement new" routine inherited from Object. In fact, this has me wondering about the practicality of this sort of checking at all. It seems a fairly straightforward design for the language to consider broken. Sean
Apr 10 2008
Sean Kelly Wrote:== Quote from Kevin Bealer (kevinbealer gmail.com)'s article... I can think of these reasons off hand why (C++) folks do placement new. 1. Allocate lots of class objects at once to reduce allocations. 2. Allocate-on-stack for objects to avoid allocation altogether. 3. Group classes together for memory locality. 4. Tricks like surrounding objects with DEADBEEF for memory corruption detection, or adding next or left/right pointers to objects. Out of curiosity, what motivates your desire for placement new? KevinIf you want to do really specific things with memory, C++ lets you do this, but in D classes can only be handled by their object references. You can't do a "placement new" or anything like it with D classes. In C++ you could build classes that automatically allocate themself in a shared memory segment, but in D, probably not. Note that in practice, this is hard to do right and I think is rarely used for much.I'd personally like for "placement new" to be supported by the language. I've considered adding a new(void*) method to Object for this purpose in Tango, but haven't experimented enough to find out if this would cause any problems.
Apr 10 2008
Kevin Bealer wrote:Sean Kelly Wrote:(2) is solved in D by using scope classes. But the others still remain vaild reasons why a placement new is useful.== Quote from Kevin Bealer (kevinbealer gmail.com)'s article... I can think of these reasons off hand why (C++) folks do placement new. 1. Allocate lots of class objects at once to reduce allocations. 2. Allocate-on-stack for objects to avoid allocation altogether. 3. Group classes together for memory locality. 4. Tricks like surrounding objects with DEADBEEF for memory corruption detection, or adding next or left/right pointers to objects. Out of curiosity, what motivates your desire for placement new? KevinIf you want to do really specific things with memory, C++ lets you do this, but in D classes can only be handled by their object references. You can't do a "placement new" or anything like it with D classes. In C++ you could build classes that automatically allocate themself in a shared memory segment, but in D, probably not. Note that in practice, this is hard to do right and I think is rarely used for much.I'd personally like for "placement new" to be supported by the language. I've considered adding a new(void*) method to Object for this purpose in Tango, but haven't experimented enough to find out if this would cause any problems.
Apr 10 2008
== Quote from Kevin Bealer (kevinbealer gmail.com)'s articleOut of curiosity, what motivates your desire for placement new?Constructing D objects in shared memory. That's also an underlying reason why I added a way to override object monitors in Tango. Sean
Apr 11 2008
Sean Kelly wrote:I'd personally like for "placement new" to be supported by the language. I've considered adding a new(void*) method to Object for this purpose in Tango, but haven't experimented enough to find out if this would cause any problems.[snip]class Object { void* new( size_t s, void* p ) { return p; } }Might I suggest that if you ever again get the urge to add placement new, you consider adding --- void* new( size_t s, void[] arr ) { assert(s <= arr.length); return arr.ptr; } --- instead?
Apr 11 2008
Frits van Bommel wrote:Sean Kelly wrote:[snip]Oh, and after reading the spec: the 'void*' in front of 'new' shouldn't be there. Like with constructors, the return type is implicit.class Object { void* new( size_t s, void* p ) { return p; } }Might I suggest that if you ever again get the urge to add placement new, you consider adding --- void* new( size_t s, void[] arr ) { assert(s <= arr.length); return arr.ptr; } --- instead?
Apr 11 2008
Sean Kelly wrote:With the vtbl checking in D, I think the above call will throw a "not implemented" message because D overrides one inherited "new" routine but not the "placement new" routine inherited from Object. In fact, this has me wondering about the practicality of this sort of checking at all. It seems a fairly straightforward design for the language to consider broken.Actually, that doesn't apply to class allocators. Since no instance exists yet, they don't do the vtable lookup; they're implicitly static. And that means calling inherited class allocators, at least from outside the class itself, is an error if a new one is defined. Also, I'm not sure if you can call an inherited allocator with 'super' as you're trying to do in class D.
Apr 11 2008
== Quote from Frits van Bommel (fvbommel REMwOVExCAPSs.nl)'s articleSean Kelly wrote:That's a slightly odd rule. I'd think that explicitly calling obj.new() would be fine since doing so shouldn't mutate the instance. Or did I misunderstand?With the vtbl checking in D, I think the above call will throw a "not implemented" message because D overrides one inherited "new" routine but not the "placement new" routine inherited from Object. In fact, this has me wondering about the practicality of this sort of checking at all. It seems a fairly straightforward design for the language to consider broken.Actually, that doesn't apply to class allocators. Since no instance exists yet, they don't do the vtable lookup; they're implicitly static. And that means calling inherited class allocators, at least from outside the class itself, is an error if a new one is defined.Also, I'm not sure if you can call an inherited allocator with 'super' as you're trying to do in class D.Really? Strange. Hm... well upon further reflection, I think this may be a special case for methods in Object, since one could argue that anyone who only wants to override a subset of overloads should add empty forwarding overloads (ie. that call super) for the remainder, for clarity. But the lack of compile-time checking still stinks... I'm still not sure it prevents more bugs than it creates. Sean
Apr 11 2008
== Quote from Sean Kelly (sean invisibleduck.org)'s article== Quote from Frits van Bommel (fvbommel REMwOVExCAPSs.nl)'s articleBah... forget everything I said. You're right of course. Someday I'll learn never to post when tired. It's just such a difficult rule to remember at the appropriate times :-) So for the record. I do think the overload checking is a good idea--it just needs to be clearly documented somewhere (if it isn't already). And the 'super' thing makes total sense--there's no instance so 'super' isn't technically valid. SeanSean Kelly wrote:That's a slightly odd rule. I'd think that explicitly calling obj.new() would be fine since doing so shouldn't mutate the instance. Or did I misunderstand?With the vtbl checking in D, I think the above call will throw a "not implemented" message because D overrides one inherited "new" routine but not the "placement new" routine inherited from Object. In fact, this has me wondering about the practicality of this sort of checking at all. It seems a fairly straightforward design for the language to consider broken.Actually, that doesn't apply to class allocators. Since no instance exists yet, they don't do the vtable lookup; they're implicitly static. And that means calling inherited class allocators, at least from outside the class itself, is an error if a new one is defined.Also, I'm not sure if you can call an inherited allocator with 'super' as you're trying to do in class D.Really? Strange. Hm... well upon further reflection, I think this may be a special case for methods in Object, since one could argue that anyone who only wants to override a subset of overloads should add empty forwarding overloads (ie. that call super) for the remainder, for clarity. But the lack of compile-time checking still stinks... I'm still not sure it prevents more bugs than it creates.
Apr 11 2008
Sean Kelly wrote:So for the record. I do think the overload checking is a good idea--it just needs to be clearly documented somewhere (if it isn't already). And the 'super' thing makes total sense--there's no instance so 'super' isn't technically valid.Aren't "super" calls bound at compile-time?
Apr 11 2008
== Quote from Robert Fraser (fraserofthenight gmail.com)'s articleSean Kelly wrote:My guess would be that a "super" call rebinds to the superclass' vtbl. I don't think it actually does a static lookup and direct function call if that's what you're suggesting, but it does seem technically possible. In any case, using "super" here may actually work in this case since the "new" method is effectively static, but it doesn't seem any more advisable to use it than you would "this" in the same situation. It's just bad style, if nothing else. SeanSo for the record. I do think the overload checking is a good idea--it just needs to be clearly documented somewhere (if it isn't already). And the 'super' thing makes total sense--there's no instance so 'super' isn't technically valid.Aren't "super" calls bound at compile-time?
Apr 11 2008
Kevin Bealer wrote:I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.
Apr 11 2008
Walter Bright wrote:Kevin Bealer wrote:Are D's templates a complete replacement in functionality for Boost's MPL ? If so could you write an article on your web site about the how's and why's of that ? I am still trying to understand D's templates based on the sparse documentation of them. Remember that part of the difficult for the Boost developer is also supporting many non-conforming C++ compilers, so part of the genius of what they are doing is manipulating around compilers that do not deal with C++ templates correctly ( perhaps because the details of the C++ template system are so abstruse and difficult to understand and implement).I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.
Apr 12 2008
== Quote from Edward Diener (eddielee_no_spam_here tropicsoft.com)'s articleWalter Bright wrote:I'm not sure if it helps, but the D book that I and some of the other Tango folks wrote has a chapter on templates. I think it's probably the most extensive "how to" document available right now. It's not free, but I believe the e-book version is only like $13.Kevin Bealer wrote:Are D's templates a complete replacement in functionality for Boost's MPL ? If so could you write an article on your web site about the how's and why's of that ? I am still trying to understand D's templates based on the sparse documentation of them.I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.Remember that part of the difficult for the Boost developer is also supporting many non-conforming C++ compilers, so part of the genius of what they are doing is manipulating around compilers that do not deal with C++ templates correctly ( perhaps because the details of the C++ template system are so abstruse and difficult to understand and implement).Exactly. Sean
Apr 12 2008
Edward Diener wrote:Walter Bright wrote:I don't really understand Boost MPL, but D's template system is considerably more powerful than C++'s. I agree that more documentation is needed, but one can easily write a book about it.Kevin Bealer wrote:Are D's templates a complete replacement in functionality for Boost's MPL ? If so could you write an article on your web site about the how's and why's of that ? I am still trying to understand D's templates based on the sparse documentation of them.I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.Remember that part of the difficult for the Boost developer is also supporting many non-conforming C++ compilers, so part of the genius of what they are doing is manipulating around compilers that do not deal with C++ templates correctly ( perhaps because the details of the C++ template system are so abstruse and difficult to understand and implement).It's amazing even not considering compiler bug workarounds. And yes, a large reason for the compiler bugs is because it is so hard to understand how it is supposed to work.
Apr 12 2008
Walter Bright wrote:Edward Diener wrote:I do not know the MPL either although I understand the general concept. It is a C++ template metaprogramming library for manipulating types at compile time so that the final result of the body of a template deals in whatever types the template metaprogramming needs to generalize for his programming task. I agree that what I currently understand of D templates looks clearer than the template system in C++ but I am not knowledgable enough to know whether it is "better", or easier to use in doing the sorts of things which Boost programmers accomplish.Walter Bright wrote:I don't really understand Boost MPL, but D's template system is considerably more powerful than C++'s.Kevin Bealer wrote:Are D's templates a complete replacement in functionality for Boost's MPL ? If so could you write an article on your web site about the how's and why's of that ? I am still trying to understand D's templates based on the sparse documentation of them.I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.I agree that more documentation is needed, but one can easily write a book about it.The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ? I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ), function ( universal callable ), bind and/or lambda ( function object creation ), shared_ptr ( sharable smart pointer, obviously for RAII in D because of GC ), signals ( generalized multicast events ), multi_index ( multiple index containers ), regex and/or xpressive ( regular expressions ), tokenizer ( generalized tokening of strings ), date_time ( date/time and time intervals ) and many others ( the above are just my favorites but I have hardly explored/used all of them ) which C++ programmers find very useful. All of these libraries depend on template metaprogramming in C++. Can their equivalents just as easily be implemented and have any of them been done already ? I have not looked at the D libraries, phobos and tango I believe they are called, so maybe I am way off base comparing the Boost libraries to what may already be in D. But I am trying to get an idea if D is capable of doing these Boost things just as easily or easier.
Apr 12 2008
Edward Diener wrote:Walter Bright wrote:Now the above is approaching the idea of this thread.Edward Diener wrote:I do not know the MPL either although I understand the general concept. It is a C++ template metaprogramming library for manipulating types at compile time so that the final result of the body of a template deals in whatever types the template metaprogramming needs to generalize for his programming task. I agree that what I currently understand of D templates looks clearer than the template system in C++ but I am not knowledgable enough to know whether it is "better", or easier to use in doing the sorts of things which Boost programmers accomplish.Walter Bright wrote:I don't really understand Boost MPL, but D's template system is considerably more powerful than C++'s.Kevin Bealer wrote:Are D's templates a complete replacement in functionality for Boost's MPL ? If so could you write an article on your web site about the how's and why's of that ? I am still trying to understand D's templates based on the sparse documentation of them.I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.I agree that more documentation is needed, but one can easily write a book about it.The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ? I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ), function ( universal callable ), bind and/or lambda ( function object creation ), shared_ptr ( sharable smart pointer, obviously for RAII in D because of GC ), signals ( generalized multicast events ), multi_index ( multiple index containers ), regex and/or xpressive ( regular expressions ), tokenizer ( generalized tokening of strings ), date_time ( date/time and time intervals ) and many others ( the above are just my favorites but I have hardly explored/used all of them ) which C++ programmers find very useful. All of these libraries depend on template metaprogramming in C++. Can their equivalents just as easily be implemented and have any of them been done already ?I have not looked at the D libraries, phobos and tango I believe they are called, so maybe I am way off base comparing the Boost libraries to what may already be in D. But I am trying to get an idea if D is capable of doing these Boost things just as easily or easier.Yes! And I think those are things that very may, who don't regularly write in this NG, really wonder about with D.
Apr 13 2008
Georg Wrede wrote:Edward Diener wrote:In Boost there is an entire metaprogramming paradigm based on a set of conventions regarding C++ templates and types, as implemented by the Boost MPL. This is despite the fact that C++ template syntax is much more abstruse than D's templates. So I was merely wondering if there is anything equivalent in D which can manipulate templates the way that the Boost MPL can. I agree that D's templates appear much easier to use but whether or not they are richer in functionality than C++ templates is something I do not know, but would love to find out about. But that would mean a comparison between what D can do with its templates as opposed to what the Boost MPL can do.Walter Bright wrote:Now the above is approaching the idea of this thread.Edward Diener wrote:I do not know the MPL either although I understand the general concept. It is a C++ template metaprogramming library for manipulating types at compile time so that the final result of the body of a template deals in whatever types the template metaprogramming needs to generalize for his programming task. I agree that what I currently understand of D templates looks clearer than the template system in C++ but I am not knowledgable enough to know whether it is "better", or easier to use in doing the sorts of things which Boost programmers accomplish.Walter Bright wrote:I don't really understand Boost MPL, but D's template system is considerably more powerful than C++'s.Kevin Bealer wrote:Are D's templates a complete replacement in functionality for Boost's MPL ? If so could you write an article on your web site about the how's and why's of that ? I am still trying to understand D's templates based on the sparse documentation of them.I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.I agree that more documentation is needed, but one can easily write a book about it.The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ? I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ), function ( universal callable ), bind and/or lambda ( function object creation ), shared_ptr ( sharable smart pointer, obviously for RAII in D because of GC ), signals ( generalized multicast events ), multi_index ( multiple index containers ), regex and/or xpressive ( regular expressions ), tokenizer ( generalized tokening of strings ), date_time ( date/time and time intervals ) and many others ( the above are just my favorites but I have hardly explored/used all of them ) which C++ programmers find very useful. All of these libraries depend on template metaprogramming in C++. Can their equivalents just as easily be implemented and have any of them been done already ?The template syntax is clearer, but I don't know if it is better, and/or why. I am a big advocate of clarity in computer languages but not if there is any loss of functionality. I do not believe that clarity should ever be sacrificed for needed functionality. That is one reason I still Taking away functionality for clarity is never the way to go, but adding clarity while keeping, or improving the same functionality, as D has done in mostr cases, is admirable. However in some areas D seems to have given away functionality for clarity, or some holy grail which few understand, as in the const debacle. I am hoping Walter will address this issue of template functionality as opposed to syntax, between C++ and D, extensively sometime in the future, hopefully in a technically neutral way ( he tends to be biased toward D fro some odd reason <g> ).I have not looked at the D libraries, phobos and tango I believe they are called, so maybe I am way off base comparing the Boost libraries to what may already be in D. But I am trying to get an idea if D is capable of doing these Boost things just as easily or easier.Yes! And I think those are things that very may, who don't regularly write in this NG, really wonder about with D.
Apr 13 2008
Edward Diener wrote:Georg Wrede wrote:It would be interesting to see what it takes to reproduce MPL in D. But here's a quickie for you, to implement a "type sequence" like mentioned here [http://www.boost.org/doc/libs/1_35_0/libs/mpl/doc/tutorial/represent ng-dimensions.html] the code looks basically like this: template boost_mpl_vector(T...) { alias T boost_mpl_vector; } Then you can do like the first example on that page: alias boost_mpl_vector!(char, short, int, long) signed_types; The next one, the int_<N> template is probably just this in D: template int_(int N) { const value = N; } Or maybe it would be struct int_(int N) { static const value = N; } Then the "vector_c" integral sequence wrapper starts to get interesting, but is probably something like this: template vector_c(T, Vals...) { alias ConstList!(int, Vals) vector_c; } ... plus one recursively defined template ConstList, which would probably be about 5-10 lines of code. Sorry, don't have time to work it through right now, but maybe someone else can pick up from there. :-) --bbEdward Diener wrote:In Boost there is an entire metaprogramming paradigm based on a set of conventions regarding C++ templates and types, as implemented by the Boost MPL. This is despite the fact that C++ template syntax is much more abstruse than D's templates. So I was merely wondering if there is anything equivalent in D which can manipulate templates the way that the Boost MPL can. I agree that D's templates appear much easier to use but whether or not they are richer in functionality than C++ templates is something I do not know, but would love to find out about. But that would mean a comparison between what D can do with its templates as opposed to what the Boost MPL can do.Walter Bright wrote:Now the above is approaching the idea of this thread.Edward Diener wrote:I do not know the MPL either although I understand the general concept. It is a C++ template metaprogramming library for manipulating types at compile time so that the final result of the body of a template deals in whatever types the template metaprogramming needs to generalize for his programming task. I agree that what I currently understand of D templates looks clearer than the template system in C++ but I am not knowledgable enough to know whether it is "better", or easier to use in doing the sorts of things which Boost programmers accomplish.Walter Bright wrote:I don't really understand Boost MPL, but D's template system is considerably more powerful than C++'s.Kevin Bealer wrote:Are D's templates a complete replacement in functionality for Boost's MPL ? If so could you write an article on your web site about the how's and why's of that ? I am still trying to understand D's templates based on the sparse documentation of them.I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.I agree that more documentation is needed, but one can easily write a book about it.The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ? I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ), function ( universal callable ), bind and/or lambda ( function object creation ), shared_ptr ( sharable smart pointer, obviously for RAII in D because of GC ), signals ( generalized multicast events ), multi_index ( multiple index containers ), regex and/or xpressive ( regular expressions ), tokenizer ( generalized tokening of strings ), date_time ( date/time and time intervals ) and many others ( the above are just my favorites but I have hardly explored/used all of them ) which C++ programmers find very useful. All of these libraries depend on template metaprogramming in C++. Can their equivalents just as easily be implemented and have any of them been done already ?The template syntax is clearer, but I don't know if it is better, and/or why. I am a big advocate of clarity in computer languages but not if there is any loss of functionality. I do not believe that clarity should ever be sacrificed for needed functionality. That is one reason I still Taking away functionality for clarity is never the way to go, but adding clarity while keeping, or improving the same functionality, as D has done in mostr cases, is admirable. However in some areas D seems to have given away functionality for clarity, or some holy grail which few understand, as in the const debacle. I am hoping Walter will address this issue of template functionality as opposed to syntax, between C++ and D, extensively sometime in the future, hopefully in a technically neutral way ( he tends to be biased toward D fro some odd reason <g> ).I have not looked at the D libraries, phobos and tango I believe they are called, so maybe I am way off base comparing the Boost libraries to what may already be in D. But I am trying to get an idea if D is capable of doing these Boost things just as easily or easier.Yes! And I think those are things that very may, who don't regularly write in this NG, really wonder about with D.
Apr 13 2008
Bill Baxter wrote:Edward Diener wrote:The ConstList will look something like template ConstList!(T, Vals...) { static if (Vals.length == 0) { alias Tuple!() ConstList; } else { alias Tuple!(int_!(Vals[0]), ConstList!(T, Vals[1..$])) ConstList; } } Except it would have to be a little more complicated to make the transition from the type T to int_ or long_ or whetever the actual constant type was. But that is also pretty easy with static if: template ConstType(T) { static if (is(T==int)) { alias int_ ConstType; } static if (is(T==long)) { alias long_ ConstType; } static if (is(T==byte)) { alias byte_ ConstType; } ... etc } There may be a radically better way to do that whole thing, though, since Tuple!() can already accept constants in addition to types. The int_ long_ etc helper types might not be necessary at all. You might want to check out std.traits, std.metastrings, std.typecons and std.typetuple from Phobos for some template metacode functions. --bbGeorg Wrede wrote:It would be interesting to see what it takes to reproduce MPL in D. But here's a quickie for you, to implement a "type sequence" like mentioned here [http://www.boost.org/doc/libs/1_35_0/libs/mpl/doc/tutorial/represent ng-dimensions.html] the code looks basically like this: template boost_mpl_vector(T...) { alias T boost_mpl_vector; } Then you can do like the first example on that page: alias boost_mpl_vector!(char, short, int, long) signed_types; The next one, the int_<N> template is probably just this in D: template int_(int N) { const value = N; } Or maybe it would be struct int_(int N) { static const value = N; } Then the "vector_c" integral sequence wrapper starts to get interesting, but is probably something like this: template vector_c(T, Vals...) { alias ConstList!(int, Vals) vector_c; }Edward Diener wrote:In Boost there is an entire metaprogramming paradigm based on a set of conventions regarding C++ templates and types, as implemented by the Boost MPL. This is despite the fact that C++ template syntax is much more abstruse than D's templates. So I was merely wondering if there is anything equivalent in D which can manipulate templates the way that the Boost MPL can. I agree that D's templates appear much easier to use but whether or not they are richer in functionality than C++ templates is something I do not know, but would love to find out about. But that would mean a comparison between what D can do with its templates as opposed to what the Boost MPL can do.Walter Bright wrote:Now the above is approaching the idea of this thread.Edward Diener wrote:I do not know the MPL either although I understand the general concept. It is a C++ template metaprogramming library for manipulating types at compile time so that the final result of the body of a template deals in whatever types the template metaprogramming needs to generalize for his programming task. I agree that what I currently understand of D templates looks clearer than the template system in C++ but I am not knowledgable enough to know whether it is "better", or easier to use in doing the sorts of things which Boost programmers accomplish.Walter Bright wrote:I don't really understand Boost MPL, but D's template system is considerably more powerful than C++'s.Kevin Bealer wrote:Are D's templates a complete replacement in functionality for Boost's MPL ? If so could you write an article on your web site about the how's and why's of that ? I am still trying to understand D's templates based on the sparse documentation of them.I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.I agree that more documentation is needed, but one can easily write a book about it.The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ? I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ), function ( universal callable ), bind and/or lambda ( function object creation ), shared_ptr ( sharable smart pointer, obviously for RAII in D because of GC ), signals ( generalized multicast events ), multi_index ( multiple index containers ), regex and/or xpressive ( regular expressions ), tokenizer ( generalized tokening of strings ), date_time ( date/time and time intervals ) and many others ( the above are just my favorites but I have hardly explored/used all of them ) which C++ programmers find very useful. All of these libraries depend on template metaprogramming in C++. Can their equivalents just as easily be implemented and have any of them been done already ?The template syntax is clearer, but I don't know if it is better, and/or why. I am a big advocate of clarity in computer languages but not if there is any loss of functionality. I do not believe that clarity should ever be sacrificed for needed functionality. That is not improvements. Taking away functionality for clarity is never the way to go, but adding clarity while keeping, or improving the same functionality, as D has done in mostr cases, is admirable. However in some areas D seems to have given away functionality for clarity, or some holy grail which few understand, as in the const debacle. I am hoping Walter will address this issue of template functionality as opposed to syntax, between C++ and D, extensively sometime in the future, hopefully in a technically neutral way ( he tends to be biased toward D fro some odd reason <g> ).I have not looked at the D libraries, phobos and tango I believe they are called, so maybe I am way off base comparing the Boost libraries to what may already be in D. But I am trying to get an idea if D is capable of doing these Boost things just as easily or easier.Yes! And I think those are things that very may, who don't regularly write in this NG, really wonder about with D.
Apr 13 2008
Bill Baxter wrote:Bill Baxter wrote:I will look into the D libraries more, especially the ones you mention. I am just coming to grips with D's templates and have also ordered a book on D which had the somewhat misleading title of dealing only with Phobos, whereas it seems to deal with the D language itself pretty extensively also. D has some really nice features but it really needs much better language documentation to attract programmers, especially C++ programmers. I am extremely good in C++ and if I have had many, many struggles trying to understand D from the specification. Since I can imagine what a less knowledgable programmer must have to go through trying to understand D for the first time, I can understand why someone else might give up based only on the documentation. Thanks for the examples above. I do realize that D has some built-in features which enable template manipulation which Boost MPL has to emulate through some very clever C++ template metaprogramming. In particular, as you have shown above, D has the tuple concept, the static if...else, and also something I like quite a bit, which is that there is no necessity for a base template upon which specializations are built but that each template can be defined with its own specializations. That last feature makes D templates really much easier to write. In other words it seems as if D should be able to do some of the Boost libraries, which makes C++ so pleasurable to use in general despite the difficulty of dealing with C++ templates, fairly easily. At the same time most of the Boost libraries are tremendously useful. I will look in the Phobos library for their equivalents to see if D has some of the same abilities in its library.Edward Diener wrote:The ConstList will look something like template ConstList!(T, Vals...) { static if (Vals.length == 0) { alias Tuple!() ConstList; } else { alias Tuple!(int_!(Vals[0]), ConstList!(T, Vals[1..$])) ConstList; } } Except it would have to be a little more complicated to make the transition from the type T to int_ or long_ or whetever the actual constant type was. But that is also pretty easy with static if: template ConstType(T) { static if (is(T==int)) { alias int_ ConstType; } static if (is(T==long)) { alias long_ ConstType; } static if (is(T==byte)) { alias byte_ ConstType; } ... etc } There may be a radically better way to do that whole thing, though, since Tuple!() can already accept constants in addition to types. The int_ long_ etc helper types might not be necessary at all. You might want to check out std.traits, std.metastrings, std.typecons and std.typetuple from Phobos for some template metacode functions.Georg Wrede wrote:It would be interesting to see what it takes to reproduce MPL in D. But here's a quickie for you, to implement a "type sequence" like mentioned here [http://www.boost.org/doc/libs/1_35_0/libs/mpl/doc/tutorial/represent ng-dimensions.html] the code looks basically like this: template boost_mpl_vector(T...) { alias T boost_mpl_vector; } Then you can do like the first example on that page: alias boost_mpl_vector!(char, short, int, long) signed_types; The next one, the int_<N> template is probably just this in D: template int_(int N) { const value = N; } Or maybe it would be struct int_(int N) { static const value = N; } Then the "vector_c" integral sequence wrapper starts to get interesting, but is probably something like this: template vector_c(T, Vals...) { alias ConstList!(int, Vals) vector_c; }Edward Diener wrote:In Boost there is an entire metaprogramming paradigm based on a set of conventions regarding C++ templates and types, as implemented by the Boost MPL. This is despite the fact that C++ template syntax is much more abstruse than D's templates. So I was merely wondering if there is anything equivalent in D which can manipulate templates the way that the Boost MPL can. I agree that D's templates appear much easier to use but whether or not they are richer in functionality than C++ templates is something I do not know, but would love to find out about. But that would mean a comparison between what D can do with its templates as opposed to what the Boost MPL can do.Walter Bright wrote:Now the above is approaching the idea of this thread.Edward Diener wrote:I do not know the MPL either although I understand the general concept. It is a C++ template metaprogramming library for manipulating types at compile time so that the final result of the body of a template deals in whatever types the template metaprogramming needs to generalize for his programming task. I agree that what I currently understand of D templates looks clearer than the template system in C++ but I am not knowledgable enough to know whether it is "better", or easier to use in doing the sorts of things which Boost programmers accomplish.Walter Bright wrote:I don't really understand Boost MPL, but D's template system is considerably more powerful than C++'s.Kevin Bealer wrote:Are D's templates a complete replacement in functionality for Boost's MPL ? If so could you write an article on your web site about the how's and why's of that ? I am still trying to understand D's templates based on the sparse documentation of them.I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.I agree that more documentation is needed, but one can easily write a book about it.The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ? I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ), function ( universal callable ), bind and/or lambda ( function object creation ), shared_ptr ( sharable smart pointer, obviously for RAII in D because of GC ), signals ( generalized multicast events ), multi_index ( multiple index containers ), regex and/or xpressive ( regular expressions ), tokenizer ( generalized tokening of strings ), date_time ( date/time and time intervals ) and many others ( the above are just my favorites but I have hardly explored/used all of them ) which C++ programmers find very useful. All of these libraries depend on template metaprogramming in C++. Can their equivalents just as easily be implemented and have any of them been done already ?The template syntax is clearer, but I don't know if it is better, and/or why. I am a big advocate of clarity in computer languages but not if there is any loss of functionality. I do not believe that clarity should ever be sacrificed for needed functionality. That is C++, not improvements. Taking away functionality for clarity is never the way to go, but adding clarity while keeping, or improving the same functionality, as D has done in mostr cases, is admirable. However in some areas D seems to have given away functionality for clarity, or some holy grail which few understand, as in the const debacle. I am hoping Walter will address this issue of template functionality as opposed to syntax, between C++ and D, extensively sometime in the future, hopefully in a technically neutral way ( he tends to be biased toward D fro some odd reason <g> ).I have not looked at the D libraries, phobos and tango I believe they are called, so maybe I am way off base comparing the Boost libraries to what may already be in D. But I am trying to get an idea if D is capable of doing these Boost things just as easily or easier.Yes! And I think those are things that very may, who don't regularly write in this NG, really wonder about with D.
Apr 14 2008
Edward Diener wrote:D has some really nice features but it really needs much better language documentation to attract programmers, especially C++ programmers.Hah, I think the same thing every time I'm forced to try to use a boost library. :-) Like just today when I had to go look at Boost::MPL to see what it was all about.In other words it seems as if D should be able to do some of the Boost libraries, which makes C++ so pleasurable to use in general despite the difficulty of dealing with C++ templates, fairly easily. At the same time most of the Boost libraries are tremendously useful. I will look in the Phobos library for their equivalents to see if D has some of the same abilities in its library.The book with the misleading title is about Tango, actually. Maybe you could tackle porting whatever you find useful about Boost::MPL to D as a first project? :-) I'm sure many here would be happy to help. (And would also be interested to find out what people find useful about Boost::MPL -- my one experience trying to use Boost::lambda sent me screaming back to good old for loops.) --bb
Apr 14 2008
Bill Baxter wrote:Edward Diener wrote:That is a little unfair as you are comparing documentation about a computer language library to documentation about a computer language itself. While I think library documentation can often be better, I am sure that computer language documentation shouold always be very good just to attract people to that language. When one is going head-to-head against the other good and popular which have many detailed books written just on the language itself, one needs to have very good documentation which enables an intelligent programmer to pick up the language easily. After 9 years of D the documentation about the language remains extremely sparse.D has some really nice features but it really needs much better language documentation to attract programmers, especially C++ programmers.Hah, I think the same thing every time I'm forced to try to use a boost library. :-) Like just today when I had to go look at Boost::MPL to see what it was all about.OK. Hopefully it will about D enough for me to pick up the particulars better than I have been able to do from the specification.In other words it seems as if D should be able to do some of the Boost libraries, which makes C++ so pleasurable to use in general despite the difficulty of dealing with C++ templates, fairly easily. At the same time most of the Boost libraries are tremendously useful. I will look in the Phobos library for their equivalents to see if D has some of the same abilities in its library.The book with the misleading title is about Tango, actually.Maybe you could tackle porting whatever you find useful about Boost::MPL to D as a first project? :-)MPL is a template metaprogramming library which is beyond me in many ways. I wouldn't try to port it to D unless it could be used to create other libraries in D. But trying to port boost::function/boost::bind might be an interesting project. I have already made the point to Walter that since D has delegates and function pointers that they should be merged into a single callable type, which is what boost::function is. Boost::bind is simply a way of creating that callable type while possibly binding arguments to values. Boost::lambda is very similar to boost::bind with a lambda-like syntax.I'm sure many here would be happy to help. (And would also be interested to find out what people find useful about Boost::MPL -- my one experience trying to use Boost::lambda sent me screaming back to good old for loops.)Really ? I always though using boost::lambda was pretty clear for the main part, while some of its esoteric usages might be a bit strange. The only problem with boost::lambda is that it takes a very conformant C++ compiler. Unfortunately Digital Mars C++ is really not quite good enough to handle many Boost libraries. I think Walter got a little tired of trying to make Digital Mars C++ follow all of the C++ standard, especially as regards templates and/or overloading, where the rules get very arcane, so that may have been another impetus toward creating D where the rules are simpler but perhaps just as effective. In a way I can see why he created D, since C++ is so slow to move forward to fix difficulties and inconsistencies in its syntax, and I am very sympathetic to not having to argue tirelessly with some of the C++ standard committee members who are so locked into the past. Even Stroustrup disappoints me with his argument about having to maintain compatibility with C seemingly forever. C++ should have dropped that necessity a long time ago and moved off on its own in order to make a language that was just as rich but easier to use. Thus D is very interesting to me because it has followed that path. I just need to learn it much better and perhaps appreciate what it can do much better before I take on any serious programming project with it.
Apr 14 2008
Bill Baxter wrote:Edward Diener wrote:"Learn to Tango with D" is definately more about D than about Tango. -- Lars Ivar Igesund blog at http://larsivi.net DSource, #d.tango & #D: larsivi Dancing the TangoD has some really nice features but it really needs much better language documentation to attract programmers, especially C++ programmers.Hah, I think the same thing every time I'm forced to try to use a boost library. :-) Like just today when I had to go look at Boost::MPL to see what it was all about.In other words it seems as if D should be able to do some of the Boost libraries, which makes C++ so pleasurable to use in general despite the difficulty of dealing with C++ templates, fairly easily. At the same time most of the Boost libraries are tremendously useful. I will look in the Phobos library for their equivalents to see if D has some of the same abilities in its library.The book with the misleading title is about Tango, actually.
Apr 14 2008
Edward Diener wrote:Thanks for the examples above. I do realize that D has some built-in features which enable template manipulation which Boost MPL has to emulate through some very clever C++ template metaprogramming. In particular, as you have shown above, D has the tuple concept, the static if...else, and also something I like quite a bit, which is that there is no necessity for a base template upon which specializations are built but that each template can be defined with its own specializations. That last feature makes D templates really much easier to write.One aspect of C++ templates is rendered completely irrelevant in D is D's ability to do compile time function execution. Any C++ metaprogramming that computes a value can be replaced in D with an ordinary function, that is then executed at compile time. Other things that help are D's ability to pass strings as template arguments, and parse those strings at compile time, and D's ability to access local variables (not just globals) from template expansions.
Apr 15 2008
Walter Bright wrote:Edward Diener wrote:I assume the first means function execution which produces a constant expression. I believe C++ has that on the plate for C++0x, but of course you have evidently have it now. I never realized that a string, by which I believe you mean a string literal, could not be passed as a template argument which is a value and not a type. It does seem an arcane area. The last point I do not follow. Surely a template can access its own member variables, but you seem to be saying that it should access local variables also where it is being instantiated. I can't imagine the usage for that since the template creator can not possibly know where his template is being used. Nonetheless, I will look at these features in order to to understand them better. Templates are fun, and I imagine that D templates will be more fun than C++ templates because they are richer and easier to use.Thanks for the examples above. I do realize that D has some built-in features which enable template manipulation which Boost MPL has to emulate through some very clever C++ template metaprogramming. In particular, as you have shown above, D has the tuple concept, the static if...else, and also something I like quite a bit, which is that there is no necessity for a base template upon which specializations are built but that each template can be defined with its own specializations. That last feature makes D templates really much easier to write.One aspect of C++ templates is rendered completely irrelevant in D is D's ability to do compile time function execution. Any C++ metaprogramming that computes a value can be replaced in D with an ordinary function, that is then executed at compile time. Other things that help are D's ability to pass strings as template arguments, and parse those strings at compile time, and D's ability to access local variables (not just globals) from template expansions.
Apr 15 2008
Edward Diener wrote:Walter Bright wrote:C++0x has a "constexpr" proposal, which is a small subset of D's compile time function execution capability. For example, constexpr cannot do recursive functions, loops, if statements, etc.One aspect of C++ templates is rendered completely irrelevant in D is D's ability to do compile time function execution. Any C++ metaprogramming that computes a value can be replaced in D with an ordinary function, that is then executed at compile time. Other things that help are D's ability to pass strings as template arguments, and parse those strings at compile time, and D's ability to access local variables (not just globals) from template expansions.I assume the first means function execution which produces a constant expression. I believe C++ has that on the plate for C++0x, but of course you have evidently have it now.I never realized that a string, by which I believe you mean a string literal, could not be passed as a template argument which is a value and not a type. It does seem an arcane area.It's used in std.algorithms for fun things like specifying the shape of the ordering function used in a sort.The last point I do not follow. Surely a template can access its own member variables, but you seem to be saying that it should access local variables also where it is being instantiated. I can't imagine the usage for that since the template creator can not possibly know where his template is being used.Yes, it can access the local variables from where it is instantiated. (What it does is expand the template into a nested function.) The template designer doesn't need to know, it's just another aliased parameter.Nonetheless, I will look at these features in order to to understand them better. Templates are fun, and I imagine that D templates will be more fun than C++ templates because they are richer and easier to use.
Apr 15 2008
Edward Diener Wrote:Walter Bright wrote:Even if C++ gets it, it'll never be as good. The real fun comes when the compile-time function returns or manipulates a string. I don't think it's possible to do that unless the language has built-in strings and string manipulation.Edward Diener wrote:I assume the first means function execution which produces a constant expression. I believe C++ has that on the plate for C++0x, but of course you have evidently have it now.Thanks for the examples above. I do realize that D has some built-in features which enable template manipulation which Boost MPL has to emulate through some very clever C++ template metaprogramming. In particular, as you have shown above, D has the tuple concept, the static if...else, and also something I like quite a bit, which is that there is no necessity for a base template upon which specializations are built but that each template can be defined with its own specializations. That last feature makes D templates really much easier to write.One aspect of C++ templates is rendered completely irrelevant in D is D's ability to do compile time function execution. Any C++ metaprogramming that computes a value can be replaced in D with an ordinary function, that is then executed at compile time. Other things that help are D's ability to pass strings as template arguments, and parse those strings at compile time, and D's ability to access local variables (not just globals) from template expansions.I never realized that a string, by which I believe you mean a string literal, could not be passed as a template argument which is a value and not a type. It does seem an arcane area.It's fundamental. AFAIK, C++ gains its Turing-completeness purely from the ability to have integral value template parameters. That's horribly clumsy. With a string, you can encode _anything_. Consequently, instead of that horrible mess you get with expression templates, where an expression is encoded as a tree of types, you can simply encode it as a string. (Particularly nice for encoding a regexp!).The last point I do not follow. Surely a template can access its own member variables, but you seem to be saying that it should access local variables also where it is being instantiated. I can't imagine the usage for that since the template creator can not possibly know where his template is being used.The name of the local variable can be passed as a template parameter.Nonetheless, I will look at these features in order to to understand them better. Templates are fun, and I imagine that D templates will be more fun than C++ templates because they are richer and easier to use.Indeed they are. Extremely addictive.
Apr 15 2008
Edward Diener wrote:The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ?Yes. See std.algorithms, for one. It is written by Andrei Alexandrescu, the guy who revolutionized template programming in C++ with his book "Modern C++ Design."I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ),I wrote a toy Spirit clone a while back, just as a proof of concept. It is very doable.function ( universal callable ), bind and/or lambda ( function object creation ),I believe that closures and delegates make those irrelevant.shared_ptr ( sharable smart pointer, obviously for RAII in D because of GC ),Coming with RAII for structs.signals ( generalized multicast events ), multi_index ( multiple index containers ),I'm not sure what those require of templates.regex and/or xpressive ( regular expressions ),Don Clugston showed how you can to regex in D.tokenizer ( generalized tokening of strings ), date_time ( date/time and time intervals ) and many others ( the above are just my favorites but I have hardly explored/used all of them ) which C++ programmers find very useful. All of these libraries depend on template metaprogramming in C++. Can their equivalents just as easily be implemented and have any of them been done already ?Since I've implemented both C++ and D templates, I know what capabilities they have. D's exceeds C++'s.I have not looked at the D libraries, phobos and tango I believe they are called, so maybe I am way off base comparing the Boost libraries to what may already be in D. But I am trying to get an idea if D is capable of doing these Boost things just as easily or easier.For one example, I reduced a whole chapter of Andrei's "Modern C++ Design" to one page of D, see std.typetuple.
Apr 15 2008
Walter Bright Wrote:Edward Diener wrote:I'd love to see some kind of page comparing D with the contents of Modern C++ Design. It'd be a good selling point for D when the hoards of disgruntled C++ programmers start looking at D. I wonder what could be done within copy right restrictions...The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ?Yes. See std.algorithms, for one. It is written by Andrei Alexandrescu, the guy who revolutionized template programming in C++ with his book "Modern C++ Design." [...] For one example, I reduced a whole chapter of Andrei's "Modern C++ Design" to one page of D, see std.typetuple.Would you be willing to add it on dsource, scrapple, etc...? I think the doost project has been inactive for a while...I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ),I wrote a toy Spirit clone a while back, just as a proof of concept. It is very doable.Unfortunately not. Function collapses *all* the various function types into one easy to use form. D has both function and delegate, so some 3rd party utility is still needed. Closures capture variables by reference. This means that creating delegates inside a foreach loop (with deferred evaluation) could fail to have the expected behavior. Bind stores stuff by value, so I still find myself using bind libraries.function ( universal callable ), bind and/or lambda ( function object creation ),I believe that closures and delegates make those irrelevant.
Apr 15 2008
Jason House wrote:Walter Bright Wrote:If you want to write such a page, I'm sure Andrei would be willing to discuss it with you.Edward Diener wrote:I'd love to see some kind of page comparing D with the contents of Modern C++ Design. It'd be a good selling point for D when the hoards of disgruntled C++ programmers start looking at D. I wonder what could be done within copy right restrictions...The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ?Yes. See std.algorithms, for one. It is written by Andrei Alexandrescu, the guy who revolutionized template programming in C++ with his book "Modern C++ Design." [...] For one example, I reduced a whole chapter of Andrei's "Modern C++ Design" to one page of D, see std.typetuple.I don't remember what I did with it <g>.Would you be willing to add it on dsource, scrapple, etc...? I think the doost project has been inactive for a while...I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ),I wrote a toy Spirit clone a while back, just as a proof of concept. It is very doable.I'm not sure that's such a big deal.Unfortunately not. Function collapses *all* the various function types into one easy to use form. D has both function and delegate, so some 3rd party utility is still needed.function ( universal callable ), bind and/or lambda ( function object creation ),I believe that closures and delegates make those irrelevant.Closures capture variables by reference. This means that creating delegates inside a foreach loop (with deferred evaluation) could fail to have the expected behavior. Bind stores stuff by value, so I still find myself using bind libraries.If you expect captured variables to be by value, sure. But I always expected them to be by reference!
Apr 15 2008
Walter Bright wrote:Jason House wrote:That'd be a nice exercise in learning to stress D :) I'm assuming Andrei won't read and reply to this post, so what would be the next step forward?Walter Bright Wrote:If you want to write such a page, I'm sure Andrei would be willing to discuss it with you.Edward Diener wrote:I'd love to see some kind of page comparing D with the contents of Modern C++ Design. It'd be a good selling point for D when the hoards of disgruntled C++ programmers start looking at D. I wonder what could be done within copy right restrictions...The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ?Yes. See std.algorithms, for one. It is written by Andrei Alexandrescu, the guy who revolutionized template programming in C++ with his book "Modern C++ Design." [...] For one example, I reduced a whole chapter of Andrei's "Modern C++ Design" to one page of D, see std.typetuple.It's a corner case. Corner case elimination is a bigger deal to me than keyword elimination.I'm not sure that's such a big deal.Unfortunately not. Function collapses *all* the various function types into one easy to use form. D has both function and delegate, so some 3rd party utility is still needed.function ( universal callable ), bind and/or lambda ( function object creation ),I believe that closures and delegates make those irrelevant.By reference is nice in many cases, but in others it's frustrating. How do you implement the following? foreach(job; queue) runthread(void delegate(){job.execute;}); (Somehow I expect someone to pick apart the example, but I hope the point is clear)Closures capture variables by reference. This means that creating delegates inside a foreach loop (with deferred evaluation) could fail to have the expected behavior. Bind stores stuff by value, so I still find myself using bind libraries.If you expect captured variables to be by value, sure. But I always expected them to be by reference!
Apr 15 2008
Jason House wrote:Walter Bright wrote:You can contact Andrei via his web site http://erdani.org/Jason House wrote:That'd be a nice exercise in learning to stress D :) I'm assuming Andrei won't read and reply to this post, so what would be the next step forward?I'd love to see some kind of page comparing D with the contents of Modern C++ Design. It'd be a good selling point for D when the hoards of disgruntled C++ programmers start looking at D. I wonder what could be done within copy right restrictions...If you want to write such a page, I'm sure Andrei would be willing to discuss it with you.No, the point isn't clear. Closures can handle multiple threads accessing it.By reference is nice in many cases, but in others it's frustrating. How do you implement the following? foreach(job; queue) runthread(void delegate(){job.execute;}); (Somehow I expect someone to pick apart the example, but I hope the point is clear)Closures capture variables by reference. This means that creating delegates inside a foreach loop (with deferred evaluation) could fail to have the expected behavior. Bind stores stuff by value, so I still find myself using bind libraries.If you expect captured variables to be by value, sure. But I always expected them to be by reference!
Apr 15 2008
Walter Bright wrote:I probably should not have rushed to make an example before running out the door. But I'll still run with the example... For each delegate, the job variable gets captured. Each delegate will have access to the job variable. In cases of defered delegate execution, changes to the job variable will affect what the delegate does. In my example, what happens if runthread is really access to a non-blocking thread pool that queues excess commands. When the thread pool gets around to running the delegate passed in, what will be in "job"? If this is done after the loop finishes, the value inside job will be the final value from opApply (or worse, corrupt). The net effect is that a queue of 50 jobs may have the final job executed 50 times, and the first 49 jobs are never run. This does not seem like correct behavior to me.No, the point isn't clear. Closures can handle multiple threads accessing it.By reference is nice in many cases, but in others it's frustrating. How do you implement the following? foreach(job; queue) runthread(void delegate(){job.execute;}); (Somehow I expect someone to pick apart the example, but I hope the point is clear)Closures capture variables by reference. This means that creating delegates inside a foreach loop (with deferred evaluation) could fail to have the expected behavior. Bind stores stuff by value, so I still find myself using bind libraries.If you expect captured variables to be by value, sure. But I always expected them to be by reference!
Apr 15 2008
Jason House wrote:For each delegate, the job variable gets captured. Each delegate will have access to the job variable. In cases of defered delegate execution, changes to the job variable will affect what the delegate does. In my example, what happens if runthread is really access to a non-blocking thread pool that queues excess commands. When the thread pool gets around to running the delegate passed in, what will be in "job"? If this is done after the loop finishes, the value inside job will be the final value from opApply (or worse, corrupt). The net effect is that a queue of 50 jobs may have the final job executed 50 times, and the first 49 jobs are never run. This does not seem like correct behavior to me.This is just the usual distinction between value and reference semantics. D does closures by reference. If you want a value, it's simple enough to make a copy. I think D's method is more powerful, because it's a lot harder to make by-value closures into by-reference than the other way around. I also believe D's method is inherently faster, because it isn't necessary to copy the values around (and there can be an arbitrary number of them, and can be arbitrarily large structs).
Apr 15 2008
Walter Bright Wrote:Jason House wrote:The only thing I'm contesting is your statement that closures eliminate the need for a bind library. While it's true they reduce the need for a bind library, they don't eliminate it.For each delegate, the job variable gets captured. Each delegate will have access to the job variable. In cases of defered delegate execution, changes to the job variable will affect what the delegate does. In my example, what happens if runthread is really access to a non-blocking thread pool that queues excess commands. When the thread pool gets around to running the delegate passed in, what will be in "job"? If this is done after the loop finishes, the value inside job will be the final value from opApply (or worse, corrupt). The net effect is that a queue of 50 jobs may have the final job executed 50 times, and the first 49 jobs are never run. This does not seem like correct behavior to me.This is just the usual distinction between value and reference semantics. D does closures by reference. If you want a value, it's simple enough to make a copy. I think D's method is more powerful, because it's a lot harder to make by-value closures into by-reference than the other way around. I also believe D's method is inherently faster, because it isn't necessary to copy the values around (and there can be an arbitrary number of them, and can be arbitrarily large structs).
Apr 16 2008
Jason House Wrote:The only thing I'm contesting is your statement that closures eliminate the need for a bind library. While it's true they reduce the need for a bind library, they don't eliminate it.Instead of call some strange bind function just create a closure taking the still unbound arguments that calles the function. I'm not a d-Programmer, but in other languages this is very easy. e.g. Haskell foo x y z = x + y + z bar f = f 9 -- Pass bar a version of foo wich has two arguments bound bar \y -> foo 1 y 7 Or Ruby: def foo (x, y, z) return x + y + z end def bar (f) return f(9) end bar |y| { foo(1, y, 7) } int foo(int x, int y, int z) { return x + y + z; } int bar (Func<int, int> f) { return f(9); } bar(y => foo(1, y, 7)); Is C++'s bind realy any simpler? int foo(int x, int y, int z) { return x + y + z; } int bar (boost:function<int(int)> const & f) { return f(9); } bar(boost::bind(foo, 1, _1, 7));
Apr 16 2008
MatBec wrote:Jason House Wrote:Here's the D version for comparison: int foo(int x, int y, int z) { return x + y + z; } int bar (int delegate(int) f) { return f(9); } bar( delegate int(int y){ return foo(1, y, 7); }); // or with inferred return type bar( (int y){ return foo(1, y, 7); }); But that won't work if you pass it a function pointer: int int_to_int(int x) { return x+5; } bar( &int_to_int ); prog.d(39): function bar (int delegate(int)) does not match parameter types (int function(int x)) prog.d(39): Error: cannot implicitly convert expression (& int_to_int) of type int function(int x) to int delegate(int) That's the main thing I'm saying. That conversion should happen implicitly. However, even then it would not be fully general bind replacement. It still would not take a class/struct with opCall or static opCall. struct Callme { int opCall(int x) { return x - 5; } } Callme c; bar( c ); //.. error bar( &c.opCall ); // this is ok, though... Maybe the 'c' in bar(c) above should also be implicitly convertable to int delegate(int)? If so then D's delegates really could eliminate the need for a bind template I think. And thereby make life easier for everyone. --bbThe only thing I'm contesting is your statement that closures eliminate the need for a bind library. While it's true they reduce the need for a bind library, they don't eliminate it.Instead of call some strange bind function just create a closure taking the still unbound arguments that calles the function. I'm not a d-Programmer, but in other languages this is very easy. e.g. Haskell foo x y z = x + y + z bar f = f 9 -- Pass bar a version of foo wich has two arguments bound bar \y -> foo 1 y 7 Or Ruby: def foo (x, y, z) return x + y + z end def bar (f) return f(9) end bar |y| { foo(1, y, 7) } int foo(int x, int y, int z) { return x + y + z; } int bar (Func<int, int> f) { return f(9); } bar(y => foo(1, y, 7)); Is C++'s bind realy any simpler? int foo(int x, int y, int z) { return x + y + z; } int bar (boost:function<int(int)> const & f) { return f(9); } bar(boost::bind(foo, 1, _1, 7));
Apr 16 2008
MatBec wrote:Jason House Wrote:All your examples as written are problem free in D as well. Your examples don't even bind local variables from the caller...The only thing I'm contesting is your statement that closures eliminate the need for a bind library. While it's true they reduce the need for a bind library, they don't eliminate it.Instead of call some strange bind function just create a closure taking the still unbound arguments that calles the function. I'm not a d-Programmer, but in other languages this is very easy.
Apr 16 2008
MatBec, el 16 de abril a las 15:40 me escribiste:Jason House Wrote:This is called partial function application[1] in Python, which includes a module to do so[2] too. In Haskell is very natural because of the lambda calculus[3]. C++0x will have something similar[4] for templates (which I'm not sure if D support via alias). [1] http://www.python.org/dev/peps/pep-0309/ [2] http://docs.python.org/lib/module-functools.html http://www.python.org/doc/2.5/whatsnew/pep-309.html [3] http://en.wikipedia.org/wiki/Lambda_calculus [4] http://en.wikipedia.org/wiki/C%2B%2B0x#Template_typedefs -- Leandro Lucarella (luca) | Blog colectivo: http://www.mazziblog.com.ar/blog/ ---------------------------------------------------------------------------- GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145 104C 949E BFB6 5F5A 8D05) ---------------------------------------------------------------------------- De tan fina la condesa, por no cagarse, reza. -- Ricardo VaporesoThe only thing I'm contesting is your statement that closures eliminate the need for a bind library. While it's true they reduce the need for a bind library, they don't eliminate it.Instead of call some strange bind function just create a closure taking the still unbound arguments that calles the function. I'm not a d-Programmer, but in other languages this is very easy. e.g. Haskell foo x y z = x + y + z bar f = f 9 -- Pass bar a version of foo wich has two arguments bound bar \y -> foo 1 y 7
Apr 21 2008
Jason House wrote:This way: foreach(job; queue) { ({ auto myjob = job; runthread(void delegate(){myjob.execute;}); })(); } And I'm pretty sure that it is only due to a bug that this doesn't work: foreach(job; queue) { auto myjob = job; runthread(void delegate(){myjob.execute;}); } (I'll file a report) Like Walter said, it's a lot harder to make by-value closures into by-reference than the other way around. You may bask in the glory of D now. :) -- Bruno Medeiros - Software Developer, MSc. in CS/E graduate http://www.prowiki.org/wiki4d/wiki.cgi?BrunoMedeiros#DBy reference is nice in many cases, but in others it's frustrating. How do you implement the following? foreach(job; queue) runthread(void delegate(){job.execute;}); (Somehow I expect someone to pick apart the example, but I hope the point is clear)Closures capture variables by reference. This means that creating delegates inside a foreach loop (with deferred evaluation) could fail to have the expected behavior. Bind stores stuff by value, so I still find myself using bind libraries.If you expect captured variables to be by value, sure. But I always expected them to be by reference!
Apr 25 2008
Walter Bright wrote:Jason House wrote:It is only a big deal in the sense that proving a single callback signature or a single event signature, rather than two of each because of the presumed need to support both delegates and function pointers, is a big deal. In other words it is much cleaner to present a single callable interface in a language, ala boost::function, Python callables, callable is a delegate or function pointer as long as the signature matches, so it is a PITA if a language can not fold both into a single callable concept. That is the issue and I think if you think about it you will realize why it is better from both a clarity and ease of use perspective to have a single callable representing both. There is no sense in a language as rich as D to have to move backward from what other other good languages are able to represent.Walter Bright Wrote:If you want to write such a page, I'm sure Andrei would be willing to discuss it with you.Edward Diener wrote:I'd love to see some kind of page comparing D with the contents of Modern C++ Design. It'd be a good selling point for D when the hoards of disgruntled C++ programmers start looking at D. I wonder what could be done within copy right restrictions...The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ?Yes. See std.algorithms, for one. It is written by Andrei Alexandrescu, the guy who revolutionized template programming in C++ with his book "Modern C++ Design." [...] For one example, I reduced a whole chapter of Andrei's "Modern C++ Design" to one page of D, see std.typetuple.I don't remember what I did with it <g>.Would you be willing to add it on dsource, scrapple, etc...? I think the doost project has been inactive for a while...I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ),I wrote a toy Spirit clone a while back, just as a proof of concept. It is very doable.I'm not sure that's such a big deal.Unfortunately not. Function collapses *all* the various function types into one easy to use form. D has both function and delegate, so some 3rd party utility is still needed.function ( universal callable ), bind and/or lambda ( function object creation ),I believe that closures and delegates make those irrelevant.
Apr 15 2008
Edward Diener wrote:I think all that's needed is a way to automatically promote a function to a delegate, right? Then D's delegates basically are the universal callable you're asking for. D needs the function type to be able to interop with C, but there's no reason as far as I know to make it illegal to assign a function to a delegate. It's just that the language doesn't currently allow it. The context pointer inside the delegate would just become null, because the function doesn't need it. --bbIt is only a big deal in the sense that proving a single callback signature or a single event signature, rather than two of each because of the presumed need to support both delegates and function pointers, is a big deal. In other words it is much cleaner to present a single callable interface in a language, ala boost::function, Python callables, callable is a delegate or function pointer as long as the signature matches, so it is a PITA if a language can not fold both into a single callable concept. That is the issue and I think if you think about it you will realize why it is better from both a clarity and ease of use perspective to have a single callable representing both. There is no sense in a language as rich as D to have to move backward from what other other good languages are able to represent.Function collapses *all* the various function types into one easy to use form. D has both function and delegate, so some 3rd party utility is still needed.I'm not sure that's such a big deal.
Apr 15 2008
Bill Baxter wrote:Edward Diener wrote:I totally agree with what you say here. When a D non-member function can be assigned to a delegate, we have delegate as our D equivalent of delegate.I think all that's needed is a way to automatically promote a function to a delegate, right? Then D's delegates basically are the universal callable you're asking for. D needs the function type to be able to interop with C, but there's no reason as far as I know to make it illegal to assign a function to a delegate. It's just that the language doesn't currently allow it. The context pointer inside the delegate would just become null, because the function doesn't need it.It is only a big deal in the sense that proving a single callback signature or a single event signature, rather than two of each because of the presumed need to support both delegates and function pointers, is a big deal. In other words it is much cleaner to present a single callable interface in a language, ala boost::function, Python if the callable is a delegate or function pointer as long as the signature matches, so it is a PITA if a language can not fold both into a single callable concept. That is the issue and I think if you think about it you will realize why it is better from both a clarity and ease of use perspective to have a single callable representing both. There is no sense in a language as rich as D to have to move backward from what other other good languages are able to represent.Function collapses *all* the various function types into one easy to use form. D has both function and delegate, so some 3rd party utility is still needed.I'm not sure that's such a big deal.
Apr 16 2008
Edward Diener wrote:It is only a big deal in the sense that proving a single callback signature or a single event signature, rather than two of each because of the presumed need to support both delegates and function pointers, is a big deal. In other words it is much cleaner to present a single callable interface in a language, ala boost::function, Python callables, callable is a delegate or function pointer as long as the signature matches, so it is a PITA if a language can not fold both into a single callable concept. That is the issue and I think if you think about it you will realize why it is better from both a clarity and ease of use perspective to have a single callable representing both. There is no sense in a language as rich as D to have to move backward from what other other good languages are able to represent.There's no reason you cannot write a template in D to do it - Andrei has done so in his std.algorithms code.
Apr 15 2008
== Quote from Walter Bright (newshound1 digitalmars.com)'s articleEdward Diener wrote:Sure, but templates don't suit every situation. It's not uncommon for APIs to have to overload on accepting a function and a delegate for flexibility. SeanIt is only a big deal in the sense that proving a single callback signature or a single event signature, rather than two of each because of the presumed need to support both delegates and function pointers, is a big deal. In other words it is much cleaner to present a single callable interface in a language, ala boost::function, Python callables, callable is a delegate or function pointer as long as the signature matches, so it is a PITA if a language can not fold both into a single callable concept. That is the issue and I think if you think about it you will realize why it is better from both a clarity and ease of use perspective to have a single callable representing both. There is no sense in a language as rich as D to have to move backward from what other other good languages are able to represent.There's no reason you cannot write a template in D to do it - Andrei has done so in his std.algorithms code.
Apr 15 2008
Sean Kelly wrote:Sure, but templates don't suit every situation. It's not uncommon for APIs to have to overload on accepting a function and a delegate for flexibility.The only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.
Apr 16 2008
On 16/04/2008, Walter Bright <newshound1 digitalmars.com> wrote:The only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.I think that all that is being suggested is that function (that which you get when you take the address of a static or global function) should implicitly cast to delegate (that which you get when you take the address of a local or member function). I suspect that could be done without too much runtime overhead.
Apr 16 2008
== Quote from Janice Caron (caron800 googlemail.com)'s articleOn 16/04/2008, Walter Bright <newshound1 digitalmars.com> wrote:I think the problem is that functions and delegates are called differently. That is, the context pointer is passed as an invisible first parameter to a delegate, while functions have no such invisible argument. Interestingly, because the first parameter of a D function is supposed to be passed in a register (EAX) on x86, I think you're right that it should be possible to allow such efficient conversion so long as the D calling convention accounts for it properly (and the platform supports such things). SeanThe only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.I think that all that is being suggested is that function (that which you get when you take the address of a static or global function) should implicitly cast to delegate (that which you get when you take the address of a local or member function).
Apr 16 2008
== Quote from Sean Kelly (sean invisibleduck.org)'s article== Quote from Janice Caron (caron800 googlemail.com)'s articleEr... forget that. A D function would obviously expect its first argument to be in EAX regardless of whether it's a delegate. Some conversion would be necessary unless I'm missing something. SeanOn 16/04/2008, Walter Bright <newshound1 digitalmars.com> wrote:I think the problem is that functions and delegates are called differently. That is, the context pointer is passed as an invisible first parameter to a delegate, while functions have no such invisible argument. Interestingly, because the first parameter of a D function is supposed to be passed in a register (EAX) on x86, I think you're right that it should be possible to allow such efficient conversion so long as the D calling convention accounts for it properly (and the platform supports such things).The only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.I think that all that is being suggested is that function (that which you get when you take the address of a static or global function) should implicitly cast to delegate (that which you get when you take the address of a local or member function).
Apr 16 2008
Sean Kelly wrote:== Quote from Sean Kelly (sean invisibleduck.org)'s articleHmm. Someone wrote a long post about this long ago and claimed to have figured out how to handle it. --bb== Quote from Janice Caron (caron800 googlemail.com)'s articleEr... forget that. A D function would obviously expect its first argument to be in EAX regardless of whether it's a delegate. Some conversion would be necessary unless I'm missing something.On 16/04/2008, Walter Bright <newshound1 digitalmars.com> wrote:I think the problem is that functions and delegates are called differently. That is, the context pointer is passed as an invisible first parameter to a delegate, while functions have no such invisible argument. Interestingly, because the first parameter of a D function is supposed to be passed in a register (EAX) on x86, I think you're right that it should be possible to allow such efficient conversion so long as the D calling convention accounts for it properly (and the platform supports such things).The only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.I think that all that is being suggested is that function (that which you get when you take the address of a static or global function) should implicitly cast to delegate (that which you get when you take the address of a local or member function).
Apr 16 2008
Sean Kelly Wrote:== Quote from Sean Kelly (sean invisibleduck.org)'s articleI'm not much of an ASM guru, but I would think that this could be done by "multiple entry point" functions, i.e. prefixes that move registers around. Non-delegate users would not pay for this code, but register-to-register "MOV" should be cheap anyway, since this part of the code only touches fields that must be touched soon anyway, and no branching, jumping, or register saving/unsaving cycles is needed, so it should be pipelinable. Pseudo ASM code: method_start: debug { assert(! this); } mov arg1, arg2 mov arg2, arg3 mov arg3, [non-register argument] (adjust stack fields to indicate 1 fewer arguments?) function_start: (code expecting a1, a2, a3) return ...; I guess this could only apply to "D linkage" functions, since we probably don't know the parentage of C linkage functions, and some won't have the special code. Kevin== Quote from Janice Caron (caron800 googlemail.com)'s articleEr... forget that. A D function would obviously expect its first argument to be in EAX regardless of whether it's a delegate. Some conversion would be necessary unless I'm missing something. SeanOn 16/04/2008, Walter Bright <newshound1 digitalmars.com> wrote:I think the problem is that functions and delegates are called differently. That is, the context pointer is passed as an invisible first parameter to a delegate, while functions have no such invisible argument. Interestingly, because the first parameter of a D function is supposed to be passed in a register (EAX) on x86, I think you're right that it should be possible to allow such efficient conversion so long as the D calling convention accounts for it properly (and the platform supports such things).The only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.I think that all that is being suggested is that function (that which you get when you take the address of a static or global function) should implicitly cast to delegate (that which you get when you take the address of a local or member function).
Apr 16 2008
Sean Kelly wrote:== Quote from Sean Kelly (sean invisibleduck.org)'s articleWell, if that doesn't work, there is nothing preventing the *changing* the D function calling ABI, right? Or are there some performance, or other issues? -- Bruno Medeiros - Software Developer, MSc. in CS/E graduate http://www.prowiki.org/wiki4d/wiki.cgi?BrunoMedeiros#D== Quote from Janice Caron (caron800 googlemail.com)'s article I think the problem is that functions and delegates are called differently. That is, the context pointer is passed as an invisible first parameter to a delegate, while functions have no such invisible argument. Interestingly, because the first parameter of a D function is supposed to be passed in a register (EAX) on x86, I think you're right that it should be possible to allow such efficient conversion so long as the D calling convention accounts for it properly (and the platform supports such things).Er... forget that. A D function would obviously expect its first argument to be in EAX regardless of whether it's a delegate. Some conversion would be necessary unless I'm missing something. Sean
Apr 27 2008
This is /not/ a quote from me. This is a quote from Sean Kelly.== Quote from Janice Caron (caron800 googlemail.com)'s article I think the problem is that functions and delegates are called differently... <snip> ... (and the platform supports such things)
Apr 27 2008
Bruno Medeiros wrote:Sean Kelly wrote:Well... I suppose the D ABI could state that if a function has a context pointer then this value is passed in a specific register (EAX), and that the register may not be used for parameter passing otherwise. Then I think it should be possible to call any D function as if it were a delegate. Sean== Quote from Sean Kelly (sean invisibleduck.org)'s articleWell, if that doesn't work, there is nothing preventing the *changing* the D function calling ABI, right? Or are there some performance, or other issues?== Quote from Janice Caron (caron800 googlemail.com)'s article I think the problem is that functions and delegates are called differently. That is, the context pointer is passed as an invisible first parameter to a delegate, while functions have no such invisible argument. Interestingly, because the first parameter of a D function is supposed to be passed in a register (EAX) on x86, I think you're right that it should be possible to allow such efficient conversion so long as the D calling convention accounts for it properly (and the platform supports such things).Er... forget that. A D function would obviously expect its first argument to be in EAX regardless of whether it's a delegate. Some conversion would be necessary unless I'm missing something.
Apr 27 2008
== Quote from Walter Bright (newshound1 digitalmars.com)'s articleSean Kelly wrote:Certainly. Templates are always faster. But they don't always suit. To choose the simplest example, let's say that I want to ship a library with no source code exposed. Templates are obviously out. Now, to support callable parameters I must either overload routines for both function and delegate simply to account for pointers to global vs. non-global callable routines, or I need to use a wrapper object to pass instead. Either way, the same efficiency is lost, and I'm stuck doing a bunch of wrapping or conversion in library code as well. Now perhaps the library is indeed the best place for this, but either way I disagree that "just use templates because they're faster" is an acceptable solution for every situation. The 80-20 rule dictates that generalized arguments about performance are baseless anyway because 80% of the time the performance difference isn't even noticeable. Rather, I would argue that in such instances elegance is of utmost importance because of its effect on code maintainability. The great thing about D is that it often manages to achieve top-tier performance in an eminently elegant manner. SeanSure, but templates don't suit every situation. It's not uncommon for APIs to have to overload on accepting a function and a delegate for flexibility.The only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.
Apr 16 2008
Sean Kelly wrote:== Quote from Walter Bright (newshound1 digitalmars.com)'s articlecallable. Something like setCallback(&fn). --bbSean Kelly wrote:Certainly. Templates are always faster. But they don't always suit. To choose the simplest example, let's say that I want to ship a library with no source code exposed. Templates are obviously out. Now, to support callable parameters I must either overload routines for both function and delegate simply to account for pointers to global vs. non-global callable routines, or I need to use a wrapper object to pass instead. Either way, the same efficiency is lost, and I'm stuck doing a bunch of wrapping or conversion in library code as well. Now perhaps the library is indeed the best place for this, but either way I disagree that "just use templates because they're faster" is an acceptable solution for every situation. The 80-20 rule dictates that generalized arguments about performance are baseless anyway because 80% of the time the performance difference isn't even noticeable. Rather, I would argue that in such instances elegance is of utmost importance because of its effect on code maintainability. The great thing about D is that it often manages to achieve top-tier performance in an eminently elegant manner.Sure, but templates don't suit every situation. It's not uncommon for APIs to have to overload on accepting a function and a delegate for flexibility.The only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.
Apr 16 2008
Walter Bright wrote:Sean Kelly wrote:The template approach means that one has to write a template for each function signature, uniting D function pointers and D delegates, which one wants to use as a callback or event in one's own code, unless of course one does the equivalent of boost::function in D for nn parameters as a generalized template solution. Finally if a delegate in D is the equivalent of an object pointer and a member function pointer, why would allowing a null pointer for the object pointer part not allow a delegate to encompass both a non-member function pointer and an object's member function pointer ? If it would, then is it really that much slower checking if the object pointer is null to decide internally in code how the delegate is called ?Sure, but templates don't suit every situation. It's not uncommon for APIs to have to overload on accepting a function and a delegate for flexibility.The only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.
Apr 16 2008
Walter Bright wrote:Sean Kelly wrote:I was reading about these a few days ago, as LLVM has support for these. Basically it's also how GCC implements its nested function extension. I figured someone else might find this link interesting! There's a link to a paper on trampolines in the article linked as well: http://gcc.gnu.org/onlinedocs/gcc/Nested-Functions.htmlSure, but templates don't suit every situation. It's not uncommon for APIs to have to overload on accepting a function and a delegate for flexibility.The only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.
Apr 18 2008
Tomas Lindquist Olsen wrote:Walter Bright wrote:So you mean if one uses GDC, then all calls to nested functions are handled using trampolines? Or only if you take the address of a nested function and try to call that? Anyway I totally don't see any problem with generating a trampoline in order to let a user assign a function pointer to a delegate pointer variable. The people who are obsessed with the performance difference can make special cases for function pointers vs delegate pointers, but the rest of just go about our merry business. --bbSean Kelly wrote:I was reading about these a few days ago, as LLVM has support for these. Basically it's also how GCC implements its nested function extension. I figured someone else might find this link interesting! There's a link to a paper on trampolines in the article linked as well: http://gcc.gnu.org/onlinedocs/gcc/Nested-Functions.htmlSure, but templates don't suit every situation. It's not uncommon for APIs to have to overload on accepting a function and a delegate for flexibility.The only way to merge function pointers with delegates is to have the compiler generate trampolines. This isn't very runtime efficient - the template approach will be faster.
Apr 18 2008
Walter Bright wrote:Edward Diener wrote:I know of Andrei and his book. The Boost MPL superceded what he had done, but that does not take away from the value of his original work.The question is: has anyone tackled in D some of the template metaprogramming tasks which various Boost programmers have accomplished with C++ ?Yes. See std.algorithms, for one. It is written by Andrei Alexandrescu, the guy who revolutionized template programming in C++ with his book "Modern C++ Design."Good to hear. Then maybe someone will write a real parser in D as rich as Spirit, or mayber someone already has. Despite C++ template's intricacy, Spirit is a monstrously wonderful piece of software. My hat is off to Joel Guzman and Hartmut Kaiser for it.I am trying to get a feel for how different, or how much easier ( or perhaps harder ) it would be to do Boost things like Spirit ( lex/yacc-like DSEL ),I wrote a toy Spirit clone a while back, just as a proof of concept. It is very doable.I believe you are wrong unless you have managed to combine all callables into a single syntax, and have a flexible binding mechanism built into the callable concept. But we had this discussion before where I pointed out that having both delegates and function pointers in D was bifurcating a common concept ( callable ), and that you should serious think about combining them, either through the languiage or perhaps a library, into one. In C++, boost::function is that library and bind/lambda essentially creates callables with various very flexible argument binding mechanisms. Perhaps D 2.0 can do all that but my reading of D 1.0 says no.function ( universal callable ), bind and/or lambda ( function object creation ),I believe that closures and delegates make those irrelevant.I hope it will eventually be coming some day with RAII via scope, per our long thread/discussion.shared_ptr ( sharable smart pointer, obviously for RAII in D because of GC ),Coming with RAII for structs.Signals are built on top of boost::function, and is essentially a multi-cast closure for any type of callable. Other than that it is probably no more template based than boost::function. But since Boost::function has to deal in types for all possibilities of function objects up to nn ( defaulted to 10 I believe ) parameters and a return type, boost::signals has to also.signals ( generalized multicast events ), multi_index ( multiple index containers ),I'm not sure what those require of templates.Yes, I realized that D has regular expressions in one of it libraries, which is great. Congratulations !regex and/or xpressive ( regular expressions ),Don Clugston showed how you can to regex in D.Good to hear. Now that I understand D templates better I can play with them a little more. I still have a gut feeling that D may need an equivalent template library like the Boost MPL for compile time type manipulation in order to achive the sort of complicated template metaprogramming usage that so many Boost libraries have in order to accomplish their ends, but I can not prove it and could be entirely wrong about it. Perhaps the Boost MPL is a way to do things with C++ templates which D already natively provides with D templates.tokenizer ( generalized tokening of strings ), date_time ( date/time and time intervals ) and many others ( the above are just my favorites but I have hardly explored/used all of them ) which C++ programmers find very useful. All of these libraries depend on template metaprogramming in C++. Can their equivalents just as easily be implemented and have any of them been done already ?Since I've implemented both C++ and D templates, I know what capabilities they have. D's exceeds C++'s.Is that why Andrei became interested in D <g> ?I have not looked at the D libraries, phobos and tango I believe they are called, so maybe I am way off base comparing the Boost libraries to what may already be in D. But I am trying to get an idea if D is capable of doing these Boost things just as easily or easier.For one example, I reduced a whole chapter of Andrei's "Modern C++ Design" to one page of D, see std.typetuple.
Apr 15 2008
Edward Diener wrote:Is that why Andrei became interested in D <g> ?I don't wish to put words in Andrei's mouth, except to say that we are really, really fortunate to have Andrei helping us out with D.
Apr 15 2008
Walter Bright wrote:Edward Diener wrote:I was largely joking, via the <g>. I am aware of Andrei butting heads with others on comp.std.c++ and comp.lang.c++ ( I have occasionally done the same myself ).Is that why Andrei became interested in D <g> ?I don't wish to put words in Andrei's mouth, except to say that we are really, really fortunate to have Andrei helping us out with D.
Apr 15 2008
Walter Bright wrote:Edward Diener wrote:[my bold above] ROTFLMHO! :-) :-) :-) :-) :-) :-) :-) Marketing talk aside, I doubt if anyone thinks even D's templates are /that/ easy. (Sorry, couldn't resist. I assume you actually meant the issue is broad enough. But I /did/ lough out aloud.)Walter Bright wrote:I don't really understand Boost MPL, but D's template system is considerably more powerful than C++'s. I agree that more documentation is needed, *but one can easily write a book about it*.Kevin Bealer wrote:Are D's templates a complete replacement in functionality for Boost's MPL ? If so could you write an article on your web site about the how's and why's of that ? I am still trying to understand D's templates based on the sparse documentation of them.I was amazed that Boost could do things like the Lambda support with _1 _2, etc. Those Boost guys are geniuses.I agree, they are geniuses. But that's really what is wrong with C++, you shouldn't have to be a genius to get advanced things done.(OT:) I think we're missing the point here. Suppose someone finds archives about C++, compiler development, C++ Standards Committee's memoranda, drafts and decrees, after /a hundred/ years have passed. Then one sees *in hindsight* how persistently and altruistically folks tackle the "hard" parts of computing, irrespectively of if they represent /actually/ Hard problems, or just something that's hard because other people did a sloppy job! I mean, today we just "live with" the C++ spec. With any distance (be it geographical (as in on the Moon) or temporal (as in looking at our times as they were some Western movies), it *immediately* becomes painfully obvious that nobody should accept such a situation without rebellion. And all the more because "C++ is The Programming Language" of our time.Remember that part of the difficult for the Boost developer is also supporting many non-conforming C++ compilers, so part of the genius of what they are doing is manipulating around compilers that do not deal with C++ templates correctly ( perhaps because the details of the C++ template system are so abstruse and difficult to understand and implement).It's amazing even not considering compiler bug workarounds. And yes, a large reason for the compiler bugs is because it is so hard to understand how it is supposed to work.
Apr 13 2008
Georg Wrede wrote:I read http://www.nwcpp.org/Downloads/2007/redcode_-_updated.pdf and upon reading it I got thinking of something else. Those familiar with C++ (aren't we all?) probably sometimes come across things that somebody has done in C++ that are simply stunning. Things that one would have thought would need a new language, or maybe just be impossible to implement at all. I know I have. (A lot of Boost stuff is like that, originally the STL got me breathless, but there's a lot that's not template related, too.) Is it just paranoia, or is C++ still more flexible and expressive than D? Are there still things you can do in C++ that are impossible or too awkward to do in D? Of course, I don't mean Obfuscated C(++). While that definitely demonstrates the unfathomable agility of the language, I'm only talking about serious, non-juvenile stuff.Structs would be my vote for the area where C++ is more flexible and expressive than D. But Walter realizes this and it's on the plate. Some sort of destructor support was added in the last update, and inheritance was promised in the slides at last year's D conference. So D will catch up in that arena. Metaprogramming is definitely the area where D is light years ahead of C++. --bb
Apr 10 2008
Structs would be my vote for the area where C++ is more flexible and expressive than D. But Walter realizes this and it's on the plate. Some sort of destructor support was added in the last update, and inheritance was promised in the slides at last year's D conference. So D will catch up in that arena. Metaprogramming is definitely the area where D is light years ahead of C++. --bbAgree on all points. Overall, D is much more elegant and expressive than C++, especially with templates. With better support for structs, D will allow more flexibility for high-performance data structures. IMO, the next steps for closing the performance gap with C++ would be to optimize the GC and the compiler back-end. Once these optimizations are in place, D should be on par with C++ performance-wise. What's more, if the right features are implemented, D performance could potentially surpass C++ in the next five years or so. -Craig
Apr 11 2008
Sean Kelly Wrote:== Quote from Kevin Bealer (kevinbealer gmail.com)'s articleI wondered about this myself -- at one point I sat down and designed a bunch of code in C++ that used relative pointers and memory mapped areas. The idea was to have a complete set of tools for created "tied" containers and so on in memory mapped files, so that you could create documents and random data structures without considering the data format itself. The relative pointer idea is that a smart pointer could be defined that actually stored the pointed to value minus the pointer's address. This allows you to point to other objects in the same memory mapped arena regardless of where it gets mapped to. It's also nearly free to use these because the address of the pointer being dereferenced is always itself in a register, so the cost of dereferencing is exactly one subtraction with no IO overhead. You can also use 32 bit pointers regardless of platform as long as your arena is <= 2GB, but you need to worry about endianness. Alternately, you could use 64 bit pointers with multi-document systems but takes more computation. Of course you need to redefine every type you use with this system -- even C++ classes that use allocator template parameters rarely come in a form that is templatized on smart-pointer type. (And if you use virtual pointers, you need to do something about that -- I had some ideas but I never finished that part of it.) KevinOut of curiosity, what motivates your desire for placement new?Constructing D objects in shared memory. That's also an underlying reason why I added a way to override object monitors in Tango. Sean
Apr 11 2008
== Quote from Kevin Bealer (kevinbealer gmail.com)'s articleSean Kelly Wrote:minus the pointer's address. This allows you to point to other objects in== Quote from Kevin Bealer (kevinbealer gmail.com)'s articleI wondered about this myself -- at one point I sat down and designed a bunch of code in C++ that used relative pointers and memory mapped areas. The idea was to have a complete set of tools for created "tied" containers and so on in memory mapped files, so that you could create documents and random data structures without considering the data format itself. The relative pointer idea is that a smart pointer could be defined that actually stored the pointed to valueOut of curiosity, what motivates your desire for placement new?Constructing D objects in shared memory. That's also an underlying reason why I added a way to override object monitors in Tango.the same memory mapped arena regardless of where it gets mapped to.It's a bit tricky, but so long as you map the file at the same address in every app using it then you can actually use absolute addressing and have it work. The tricky bit ends up being making sure that the vtbl pointers are valid, etc. I actually worked on a (patented) object database type system that stores all of its data as memory-mapped C++ objects which are used directly from their mapped location using such tricks. It's unbelievably fast and does all the mapping and unmapping automatically as the applications run. I'd do something comparable for D but for my exposure to the project--it's just too much of an IP risk, even not considering the patent.Of course you need to redefine every type you use with this system -- even C++ classes that use allocatortemplate parameters rarely come in a form that is templatized on smart-pointer type. (And if you use virtual pointers, you need to do something about that -- I had some ideas but I never finished that part of it.) In C++ you can supply a custom allocator that typedefs those smart pointers as the pointer type. As much as those allocators complicate container design in C++, they offer an incredibly flexible design. If you wanted to, I suspect you could even make an STL allocator that used a SQL database for storage. Sean
Apr 11 2008
I can't follow the newsgroup now, but I'd really like to know if you can use D to implement the tricks used by the Blitz++ C++ lib (http://www.oonumerics.org/blitz/ ). bearophile
Apr 15 2008
On 15/04/2008, bearophile <bearophileHUGS lycos.com> wrote:I can't follow the newsgroup now, but I'd really like to know if you can use D to implement the tricks used by the Blitz++ C++ lib (http://www.oonumerics.org/blitz/ ).Given that D templates are way, way, /way/ more powerful than C++ templates, what's to stop you?
Apr 15 2008
Janice Caron wrote:On 15/04/2008, bearophile <bearophileHUGS lycos.com> wrote:The fact that D structs are way way /way/ more wimpy than C++ structs. :-) But that's changing. Also that argument deduction in D templates isn't very complete. Nested types mess it up, like Mike Parker found just recently in another thread. Lack of template overloading and of overloading across modules can cause headaches too. requires that you use various shades of "unnatural" syntax like expr.AssignTo(r) instead of r = expr: http://www.codeproject.com/KB/recipes/dynmatrixmath.aspx D could at least do better than that, I'm sure. --bbI can't follow the newsgroup now, but I'd really like to know if you can use D to implement the tricks used by the Blitz++ C++ lib (http://www.oonumerics.org/blitz/ ).Given that D templates are way, way, /way/ more powerful than C++ templates, what's to stop you?
Apr 15 2008
Edward Diener Wrote:Bill Baxter wrote:I think it's reasonable -- boost is increasingly looking like a standard library for C++; it can be compared to D's library docs, at least. Your point about D's docs is valid, though -- they could certainly be better.Edward Diener wrote:That is a little unfair as you are comparing documentation about a computer language library to documentation about a computer language itself.D has some really nice features but it really needs much better language documentation to attract programmers, especially C++ programmers.Hah, I think the same thing every time I'm forced to try to use a boost library. :-) Like just today when I had to go look at Boost::MPL to see what it was all about.My opinion (as the technical reviewer of the book) was that the template section discussed things from a C++ mindset, which is probably helpful for a C++ programmer; yet it gives less detail on the interesting unique-to-D stuff which renders many C++ techniques obsolete. The underlying "problem" is that about a year ago, Walter suddenly stuffed a raft of enormously powerful features into the language in a very short space of time. Suddenly we had tuples, string mixins, and CTFE, and D wasn't playing catch-up with C++ any more. The showcase examples of template metaprogramming became obsolete overnight. We still haven't worked out the idioms for how to use it all; there are some fascinating synergies with existing features. Which makes documentation, especially the most useful "how-to" kind quite difficult to write at this stage. But I reckon a "metaprogramming tips and tricks" Wiki page would be pretty useful. -Don.The book with the misleading title is about Tango, actually.OK. Hopefully it will about D enough for me to pick up the particulars better than I have been able to do from the specification.
Apr 15 2008
== Quote from Don Clugston (nospam nospam.com)'s articleEdward Diener Wrote:helpful for a C++ programmer; yet it gives less detail on the interesting unique-to-D stuff which renders many C++ techniques obsolete. Yup. That was a somewhat contentious decision on my part. Since C++ is the only other language with templates I wanted to be sure the reader understood templates in general with the hope that it would provide a good base to build on. As a result, because of the length limitation of the book, the chapter doesn't talk too much about some of the newer or more advanced features that D offers such as tuples. Regarding "Tango with D" in general though... very little of the book is Tango-specific. We made a deliberate effort to make the language our primary focus. SeanOK. Hopefully it will about D enough for me to pick up the particulars better than I have been able to do from the specification.My opinion (as the technical reviewer of the book) was that the template section discussed things from a C++ mindset, which is probably
Apr 15 2008
On Tue, 15 Apr 2008 21:37:41 +0000, Sean Kelly wrote:== Quote from Don Clugston (nospam nospam.com)'s articleI would like to compliment that effort, as it is IMO that the book was very well section in terms of what is D and what is Tango. I also think the book was very well written by all authors. I hope a book that goes into more of the specialties and details of D can be written with this quality.Edward Diener Wrote:helpful for a C++ programmer; yet it gives less detail on the interesting unique-to-D stuff which renders many C++ techniques obsolete. Yup. That was a somewhat contentious decision on my part. Since C++ is the only other language with templates I wanted to be sure the reader understood templates in general with the hope that it would provide a good base to build on. As a result, because of the length limitation of the book, the chapter doesn't talk too much about some of the newer or more advanced features that D offers such as tuples. Regarding "Tango with D" in general though... very little of the book is Tango-specific. We made a deliberate effort to make the language our primary focus. SeanOK. Hopefully it will about D enough for me to pick up the particulars better than I have been able to do from the specification.My opinion (as the technical reviewer of the book) was that the template section discussed things from a C++ mindset, which is probably
Apr 15 2008