Re: free func "front" is not picked up as a candidate when doing range.front(...)
On Thursday, February 08, 2018 21:58:39 aliak via Digitalmars-d-learn wrote: > On Thursday, 8 February 2018 at 19:32:42 UTC, Jonathan M Davis > > wrote: > > On Thursday, February 08, 2018 08:18:20 aliak via > > > > Digitalmars-d-learn wrote: > >> On Thursday, 8 February 2018 at 07:16:43 UTC, Jonathan M Davis > >> > >> wrote: > >> > It would be a disaster if free functions could override > >> > member functions. For starters, it would be impossible to > >> > call the member function if that were allowed, whereas you > >> > can always call a free function by not using UFCS. And in > >> > general, it's far more desirable to have member function > >> > functions override free functions, because then you can do > >> > stuff like have have a range override find if it can provide > >> > a more efficient implementation than std.algorithm.find. > >> > >> That could be fixed with a precedence rule though no? Then > >> member find will be preferred over free find. And it won't be > >> impossible to call member functions. > > > > That's exactly how it works now. If you call a function as if > > it were a member function, and that type has that member > > function, then it's that member function that gets called. If > > that type doesn't have that member function, then free > > functions are checked. > > Wait no, that's not how it works now. Right now if a member > function with the same name exists, then free functions are not > even checked. Whereas if there's a precedence rule that prefers > member functions, then free functions will still be checked if no > member function with that name can be deduced as a viable > candidate. How it is now disregards free functions without any > consideration (if I've understood correctly), whereas I'm asking > why free functions are not even considered if a member function > is not an actual candidate. I'm not asking about overriding > member functions with free functions. > > i.e. in my original post, the free function front(int) does not > exist in type FilterResult. D tends to be very picky about what it puts in overload sets in order to avoid function hijacking - e.g. it doesn't even include base class functions in an overload set once you've declared one in a derived class unless you explicitly add an alias to the base class function in the derived class. Also, D doesn't support "best match" with function overloads. The matches have to be exact - e.g. as soon as implicit conversions come into play, there can only be one match. If there's ever a conflict, you get a compilation error (unlike in C++, which tries to figure out what it thinks the best match is and go with that, sometimes with surprising results). And having both the member functions and free functions in the same overload set would basically require the compiler to go with the "best match," which simply isn't how D deals with overloads. Sometimes, that's annoying, but it also prevents a lot of subtle bugs that tend to crop up in C++ code. https://dlang.org/spec/function.html#function-overloading https://dlang.org/articles/hijack.html - Jonathan M Davis
Re: free func "front" is not picked up as a candidate when doing range.front(...)
On Thursday, 8 February 2018 at 19:32:42 UTC, Jonathan M Davis wrote: On Thursday, February 08, 2018 08:18:20 aliak via Digitalmars-d-learn wrote: On Thursday, 8 February 2018 at 07:16:43 UTC, Jonathan M Davis wrote: > It would be a disaster if free functions could override > member functions. For starters, it would be impossible to > call the member function if that were allowed, whereas you > can always call a free function by not using UFCS. And in > general, it's far more desirable to have member function > functions override free functions, because then you can do > stuff like have have a range override find if it can provide > a more efficient implementation than std.algorithm.find. That could be fixed with a precedence rule though no? Then member find will be preferred over free find. And it won't be impossible to call member functions. That's exactly how it works now. If you call a function as if it were a member function, and that type has that member function, then it's that member function that gets called. If that type doesn't have that member function, then free functions are checked. Wait no, that's not how it works now. Right now if a member function with the same name exists, then free functions are not even checked. Whereas if there's a precedence rule that prefers member functions, then free functions will still be checked if no member function with that name can be deduced as a viable candidate. How it is now disregards free functions without any consideration (if I've understood correctly), whereas I'm asking why free functions are not even considered if a member function is not an actual candidate. I'm not asking about overriding member functions with free functions. i.e. in my original post, the free function front(int) does not exist in type FilterResult. Cheers, - Ali
Re: what's the point of function template declarations if they can't be defined?
On Thursday, February 08, 2018 20:16:22 Marc via Digitalmars-d-learn wrote: > What's a di file? (sorry google didn't help with that) I"m not sure where the documentation for it is, but it's the D equivalent of a header file. Basically, it's essentially the same as a .d file except that it's only imported, never compiled. So, it just contains declarations and stuff that has to be defined in order to be used when importing (e.g. templates and anything used during CTFE has to be in the .di file). It's essentially a stripped down version of the .d file. So, if a library is going to use a .di file, it declares a .d file as per normal, and that's compiled into the library, but then a .di file is distributed with the library instead of a .d file, and that's what a program using the library would import instead of the .d file. The import itself doesn't change in any way, but the program then only sees what's declared in the .di version of the module instead of the .d version. The whole reason that .di files exist is to provide a way for someone to distribute a library without distributing the full source (which is something that companies often like to do). It's a pretty restrictive feature though, since templates still have to be in the .di file, and if something isn't defined in the .di file instead of just declared, then it can't be used with CTFE. And with how much templates and CTFE gets used in a lot of D code, that tends to mean that either you give up on those features, or you're forced to put a lot of your implementation in the .di file anyway, making them kind of useless. So, most of use don't go anywhere near .di files, and personally, I wish that the feature didn't exist, but it's the kind of thing that some companies insist on. - Jonathan M Davis
Debugging on Windows
Hi, is there any way to debug binaries on Windows? I'd at least like to know which line of code made it crash. If it's D code, I get a call trace usually, but if it's a call to a C library, I get a crash and that's it. I am using VSCode and I'd prefer to debug in it if possible, but using other IDEs is a possibility for me if that will help.
Re: String to binary conversation
On Monday, 5 February 2018 at 18:40:40 UTC, Steven Schveighoffer wrote: On 2/5/18 1:27 PM, Vino wrote: Hi All, Request your help on how to convert a string to binary,eg "test" to 01110100 01100101 01110011 01110100. import std.stdio, std.string; writefln("%(%b %)", "test".representation); -Steve whoa, what isn't built-in in D...
Re: what's the point of function template declarations if they can't be defined?
On Thursday, 8 February 2018 at 20:16:22 UTC, Marc wrote: What's a di file? (sorry google didn't help with that) A di file is just a D file that, by convention, only has function signatures without bodies.
Re: Debugging bad requests with vibe
On Thursday, 8 February 2018 at 17:09:44 UTC, Nicholas Wilson wrote: I have set up a vibe.d rest interface (on a server) and have a client on my machine. struct Observation { string desc; DateTime time; } interface Obsever { @property void observe(Observation ra); } void main() { auto test = Observation("a duck", cast(DateTime)Clock.currTime(UTC())); auto client = new RestInterfaceClient! Obsever("http://example.com/observation;); client. observe = test; // 400 } I' pretty sure the url is correct because other ones give 404. Is there a way I can see/log what requests are being made? I can change both the client and server. Never mind, it was because I was accidentally shadowing that path with a get on the server.
Re: Vibe.d rest & web service?
On Wednesday, 7 February 2018 at 18:47:05 UTC, Steven Schveighoffer wrote: Yes you can, but it's not pretty. interface MyInterface { void postGiveMeData(SomeData d); } class MyInterfaceImpl : MyInterface { void postGiveMeData(SomeData d) { ... } void getPage() { ... } void index() { ... } } auto myI = new MyInterfaceImpl; router.registerRestInterface(myI); router.get("/route/to/getPage", ); router.get("/route/to/index", ); This worked for me, but note that my "non-rest" function was static, so I didn't need to worry about instances. I'm not sure if the above works exactly right for you. However, I would recommend actually not doing this for your purpose. My case was different -- I still wanted routes that were REST routes, but I wanted to control the result streaming (the vibe.d return value doesn't work with ranges, so I would have had to construct essentially my entire database in an array so I could return it). In your case, I think you are better off using 2 classes, and one shared data storage area. -Steve Thanks! (Some how I missed your post).
Re: what's the point of function template declarations if they can't be defined?
On Thursday, 8 February 2018 at 07:21:05 UTC, Jonathan M Davis wrote: On Wednesday, February 07, 2018 13:39:55 Timothee Cour via Digitalmars-d- learn wrote: [...] It's useful with stuff like version(Ddoc). [...] What's a di file? (sorry google didn't help with that) It's been my understanding that it's always been illegal to provide a definition for a function that was declared previously unless it was declared in a .di file, in which case, you're not really both declaring and defining it, but the .d file is used when the module is compiled, and the .di file is used by other modules which use that module, so the declaration and definition are not seen by the same run of the compiler. - Jonathan M Davis
Re: what's the point of function template declarations if they can't be defined?
makes sense to show these (version X11), but that could be done using dmd and a special flag instead of having to rely on a new parser (which would need to be kept updated) On Thu, Feb 8, 2018 at 6:49 AM, Adam D. Ruppe via Digitalmars-d-learnwrote: > On Thursday, 8 February 2018 at 09:42:08 UTC, Timothee Cour wrote: >> >> I guess you mean `version(StdDdoc)` ? >> >> On that note, I see things like this, which are not DRY: > > > This is actually one of the reasons why I abandoned dmd for my dpldocs.info > fork and used an independent parser. > > dmd tries to build docs as it builds the program, but these are slightly > contradictory - when building the program, you need to honor versioned out > blocks. When building the docs, you just want it documented, not ignored. > dmd is (rightfully) prioritized toward building actual code, but that leaves > doc generation a bit second-hand. > > To work around dmd's clashing goals, version(StdDdoc) manually makes a > separate doc branch. > > Whereas my doc generator just shows them all, bringing the version into the > definition. > http://dpldocs.info/experimental-docs/arsd.simpledisplay.XDisplayConnection.html >
Re: free func "front" is not picked up as a candidate when doing range.front(...)
On Thursday, February 08, 2018 08:18:20 aliak via Digitalmars-d-learn wrote: > On Thursday, 8 February 2018 at 07:16:43 UTC, Jonathan M Davis > > wrote: > > It would be a disaster if free functions could override member > > functions. For starters, it would be impossible to call the > > member function if that were allowed, whereas you can always > > call a free function by not using UFCS. And in general, it's > > far more desirable to have member function functions override > > free functions, because then you can do stuff like have have a > > range override find if it can provide a more efficient > > implementation than std.algorithm.find. > > That could be fixed with a precedence rule though no? Then member > find will be preferred over free find. And it won't be impossible > to call member functions. That's exactly how it works now. If you call a function as if it were a member function, and that type has that member function, then it's that member function that gets called. If that type doesn't have that member function, then free functions are checked. > Also, in this case where it's an overload, and not an override, > it's very clear what should be called isn't it? > > In the case of an override I "feel" it may indeed be a disaster, > but not for the reasons you've stated above though, also not for > any reasons I can think of :) Hijacking maybe? But then again, if > I have a free function and then decide to make a member function > I'm hijacking the free function... hmm. D has a lot of decisions geared towards avoiding function hijacking, and when UFCS was added to the language, it was very purposefully decided that member functions would win over free functions. It is highly unlikely that that's going to change. Any such change would require a DIP which explained in detail the pros and cons of the change and why it either wouldn't break any existing code or why the code breakage would be worth it and how the transition would work. - Jonathan M Davis
Debugging bad requests with vibe
I have set up a vibe.d rest interface (on a server) and have a client on my machine. struct Observation { string desc; DateTime time; } interface Obsever { @property void observe(Observation ra); } void main() { auto test = Observation("a duck", cast(DateTime)Clock.currTime(UTC())); auto client = new RestInterfaceClient! Obsever("http://example.com/observation;); client. observe = test; // 400 } I' pretty sure the url is correct because other ones give 404. Is there a way I can see/log what requests are being made? I can change both the client and server.
Re: what's the point of function template declarations if they can't be defined?
On Thursday, 8 February 2018 at 09:42:08 UTC, Timothee Cour wrote: I guess you mean `version(StdDdoc)` ? On that note, I see things like this, which are not DRY: This is actually one of the reasons why I abandoned dmd for my dpldocs.info fork and used an independent parser. dmd tries to build docs as it builds the program, but these are slightly contradictory - when building the program, you need to honor versioned out blocks. When building the docs, you just want it documented, not ignored. dmd is (rightfully) prioritized toward building actual code, but that leaves doc generation a bit second-hand. To work around dmd's clashing goals, version(StdDdoc) manually makes a separate doc branch. Whereas my doc generator just shows them all, bringing the version into the definition. http://dpldocs.info/experimental-docs/arsd.simpledisplay.XDisplayConnection.html
Re: what's the point of function template declarations if they can't be defined?
On 2018-02-07 22:39, Timothee Cour wrote: ``` void fun_bad3(T)(T a); // declaration [1] void fun_bad3(T)(T a){}; // definition [2] void test(){ fun_bad3(1); } ``` Error: test_all.fun_bad3 called with argument types (int) matches both: main.d(11): test_all.fun_bad3!int.fun_bad3(int a) and: main.d(12): test_all.fun_bad3!int.fun_bad3(int a) should [1] be allowed? compler doens't allow defining it afterwards in [2] (unlike function definitions, and, well, modulo this regression https://issues.dlang.org/show_bug.cgi?id=18393) Perhaps if it's defined in another file. -- /Jacob Carlborg
Re: are scope guards (scope(exit, success, failure)) zero-cost abstractions?
On Thursday, 8 February 2018 at 11:23:43 UTC, Daniel Kozak wrote: I mean scope(success), for scope(exit) there is no speed penalty On Thu, Feb 8, 2018 at 12:03 PM, Daniel Kozakwrote: Yes, it add, but is almost zero On Thu, Feb 8, 2018 at 12:00 PM, Timothee Cour via Digitalmars-d-learn < digitalmars-d-learn@puremagic.com> wrote: I know that, my question is whether it adds any runtime overhead over naive way (which is to call the "bar" finalizer before each return statement) in the case where no exception is thrown On Thu, Feb 8, 2018 at 2:44 AM, Mike Parker via Digitalmars-d-learn wrote: > On Thursday, 8 February 2018 at 10:09:12 UTC, Timothee Cour > wrote: >> >> I'm curious whether scope guards add any cost over the >> naive way, eg: >> >> ``` >> void fun(){ >> ... >> scope(success) {bar;} >> ... >> } >> ``` >> >> vs: >> >> ``` >> void fun(){ >> ... >> if(foo1){ >> bar; // add this before each return >> return; >> } >> ... >> bar; >> return; >> } >> ``` >> >> For scope(success) and scope(failure), the naive way would >> anyway >> involve try/catch statements but what about scope(exit)? >> Does the >> zero-cost exception model (zero cost being for non-thrown >> exceptions) >> guarantee us that scope(success) has 0 overhead over naive >> way? > > > Scope guards are lowered to the equivalent > try/catch/finally blocks anyway. Yes, it's easy to see this when looking at the lowered AST and ASM. 1) AST https://run.dlang.io/is/KNJbnP --- import object; import core.stdc.stdio; void main() { printf("%s", "All good."); printf("%s", "FOO"); return 0; } --- 2) ASM https://run.dlang.io/is/bIVYvi --- _Dmain: pushRBP mov RBP,RSP lea RSI,FLAT:.rodata[00h][RIP] lea RDI,FLAT:.rodata[00h][RIP] xor EAX,EAX call printf@PLT32 lea RSI,FLAT:.rodata[00h][RIP] lea RDI,FLAT:.rodata[00h][RIP] xor EAX,EAX call printf@PLT32 xor EAX,EAX pop RBP ret ---
Re: are scope guards (scope(exit, success, failure)) zero-cost abstractions?
On Thursday, 8 February 2018 at 10:44:37 UTC, Mike Parker wrote: On Thursday, 8 February 2018 at 10:09:12 UTC, Timothee Cour wrote: I'm curious whether scope guards add any cost over the naive way, eg: ``` void fun(){ ... scope(success) {bar;} ... } ``` vs: ``` void fun(){ ... if(foo1){ bar; // add this before each return return; } ... bar; return; } ``` For scope(success) and scope(failure), the naive way would anyway involve try/catch statements but what about scope(exit)? Does the zero-cost exception model (zero cost being for non-thrown exceptions) guarantee us that scope(success) has 0 overhead over naive way? Scope guards are lowered to the equivalent try/catch/finally blocks anyway. Yes, let's look at it: ``` scope(failure) printf("%s", "error".ptr); printf("%s", "All good.".ptr); ``` 1) Lowered AST https://run.dlang.io/is/PmRfkb --- import object; import core.stdc.stdio; void main() { try { printf("%s", "All good."); } catch(Throwable __o2) { printf("%s", "error"); throw __o2; } return 0; } --- 2) Assembly (reduced to the interesting bits - see https://run.dlang.io/is/Cafgja for the full ASM) --- call printf@PLT32 jmp short L69 lea RSP,0FFF0h[RBP] mov -8[RBP],EDX mov RDI,RAX call __dmd_begin_catch@PLT32 mov -010h[RBP],RAX mov EAX,-8[RBP] cmp EAX,1 je L3F jmp short L62 L3F:lea RSI,FLAT:.rodata[00h][RIP] lea RDI,FLAT:.rodata[00h][RIP] xor EAX,EAX call printf@PLT32 mov RDI,-010h[RBP] call _d_throwdwarf@PLT32 mov RSP,RBP pop RBP ret ---
Re: are scope guards (scope(exit, success, failure)) zero-cost abstractions?
Yes, it add, but is almost zero On Thu, Feb 8, 2018 at 12:00 PM, Timothee Cour via Digitalmars-d-learn < digitalmars-d-learn@puremagic.com> wrote: > I know that, my question is whether it adds any runtime overhead over > naive way (which is to call the "bar" finalizer before each return > statement) in the case where no exception is thrown > > > On Thu, Feb 8, 2018 at 2:44 AM, Mike Parker via Digitalmars-d-learn >wrote: > > On Thursday, 8 February 2018 at 10:09:12 UTC, Timothee Cour wrote: > >> > >> I'm curious whether scope guards add any cost over the naive way, eg: > >> > >> ``` > >> void fun(){ > >> ... > >> scope(success) {bar;} > >> ... > >> } > >> ``` > >> > >> vs: > >> > >> ``` > >> void fun(){ > >> ... > >> if(foo1){ > >> bar; // add this before each return > >> return; > >> } > >> ... > >> bar; > >> return; > >> } > >> ``` > >> > >> For scope(success) and scope(failure), the naive way would anyway > >> involve try/catch statements but what about scope(exit)? Does the > >> zero-cost exception model (zero cost being for non-thrown exceptions) > >> guarantee us that scope(success) has 0 overhead over naive way? > > > > > > Scope guards are lowered to the equivalent try/catch/finally blocks > anyway. >
Re: are scope guards (scope(exit, success, failure)) zero-cost abstractions?
I mean scope(success), for scope(exit) there is no speed penalty On Thu, Feb 8, 2018 at 12:03 PM, Daniel Kozakwrote: > Yes, it add, but is almost zero > > On Thu, Feb 8, 2018 at 12:00 PM, Timothee Cour via Digitalmars-d-learn < > digitalmars-d-learn@puremagic.com> wrote: > >> I know that, my question is whether it adds any runtime overhead over >> naive way (which is to call the "bar" finalizer before each return >> statement) in the case where no exception is thrown >> >> >> On Thu, Feb 8, 2018 at 2:44 AM, Mike Parker via Digitalmars-d-learn >> wrote: >> > On Thursday, 8 February 2018 at 10:09:12 UTC, Timothee Cour wrote: >> >> >> >> I'm curious whether scope guards add any cost over the naive way, eg: >> >> >> >> ``` >> >> void fun(){ >> >> ... >> >> scope(success) {bar;} >> >> ... >> >> } >> >> ``` >> >> >> >> vs: >> >> >> >> ``` >> >> void fun(){ >> >> ... >> >> if(foo1){ >> >> bar; // add this before each return >> >> return; >> >> } >> >> ... >> >> bar; >> >> return; >> >> } >> >> ``` >> >> >> >> For scope(success) and scope(failure), the naive way would anyway >> >> involve try/catch statements but what about scope(exit)? Does the >> >> zero-cost exception model (zero cost being for non-thrown exceptions) >> >> guarantee us that scope(success) has 0 overhead over naive way? >> > >> > >> > Scope guards are lowered to the equivalent try/catch/finally blocks >> anyway. >> > >
Re: Vibe.d rest & web service?
On Thursday, 8 February 2018 at 10:51:39 UTC, Arjan wrote: On Wednesday, 7 February 2018 at 20:23:10 UTC, Nicholas Wilson wrote: On Wednesday, 7 February 2018 at 19:50:31 UTC, Jacob Carlborg wrote: Have you tried this? No. But apart from the fact that I forgot to make the class inherit from an interface to that the rest interface would actually compile, the web interface is routed before the rest interface and so the rest interface would never be reached since the methods are all the same and the REST's are shadowed by the web's . Makes me wonder whether or not vibe does honor the http request Accept headers? e.g.: application/json or application/javascript or text/html etc. Hmm, I hadn't considered the Accept Headers.
Re: are scope guards (scope(exit, success, failure)) zero-cost abstractions?
I know that, my question is whether it adds any runtime overhead over naive way (which is to call the "bar" finalizer before each return statement) in the case where no exception is thrown On Thu, Feb 8, 2018 at 2:44 AM, Mike Parker via Digitalmars-d-learnwrote: > On Thursday, 8 February 2018 at 10:09:12 UTC, Timothee Cour wrote: >> >> I'm curious whether scope guards add any cost over the naive way, eg: >> >> ``` >> void fun(){ >> ... >> scope(success) {bar;} >> ... >> } >> ``` >> >> vs: >> >> ``` >> void fun(){ >> ... >> if(foo1){ >> bar; // add this before each return >> return; >> } >> ... >> bar; >> return; >> } >> ``` >> >> For scope(success) and scope(failure), the naive way would anyway >> involve try/catch statements but what about scope(exit)? Does the >> zero-cost exception model (zero cost being for non-thrown exceptions) >> guarantee us that scope(success) has 0 overhead over naive way? > > > Scope guards are lowered to the equivalent try/catch/finally blocks anyway.
Re: Vibe.d rest & web service?
On Wednesday, 7 February 2018 at 20:23:10 UTC, Nicholas Wilson wrote: On Wednesday, 7 February 2018 at 19:50:31 UTC, Jacob Carlborg wrote: Have you tried this? No. But apart from the fact that I forgot to make the class inherit from an interface to that the rest interface would actually compile, the web interface is routed before the rest interface and so the rest interface would never be reached since the methods are all the same and the REST's are shadowed by the web's . Makes me wonder whether or not vibe does honor the http request Accept headers? e.g.: application/json or application/javascript or text/html etc.
Re: are scope guards (scope(exit, success, failure)) zero-cost abstractions?
On Thursday, 8 February 2018 at 10:09:12 UTC, Timothee Cour wrote: I'm curious whether scope guards add any cost over the naive way, eg: ``` void fun(){ ... scope(success) {bar;} ... } ``` vs: ``` void fun(){ ... if(foo1){ bar; // add this before each return return; } ... bar; return; } ``` For scope(success) and scope(failure), the naive way would anyway involve try/catch statements but what about scope(exit)? Does the zero-cost exception model (zero cost being for non-thrown exceptions) guarantee us that scope(success) has 0 overhead over naive way? Scope guards are lowered to the equivalent try/catch/finally blocks anyway.
Re: are scope guards (scope(exit, success, failure)) zero-cost abstractions?
likewise, will scope(exit) add any overhead over naive code in the case where no exception is thrown? ``` void fun(){ ... scope(success) {bar;} ... } vs void fun(){ ... if(foo1){ bar; // add this before each return return; } ... bar; return; } ``` On Thu, Feb 8, 2018 at 2:09 AM, Timothee Courwrote: > I'm curious whether scope guards add any cost over the naive way, eg: > > ``` > void fun(){ > ... > scope(success) {bar;} > ... > } > ``` > > vs: > > ``` > void fun(){ > ... > if(foo1){ > bar; // add this before each return > return; > } > ... > bar; > return; > } > ``` > > For scope(success) and scope(failure), the naive way would anyway > involve try/catch statements but what about scope(exit)? Does the > zero-cost exception model (zero cost being for non-thrown exceptions) > guarantee us that scope(success) has 0 overhead over naive way?
are scope guards (scope(exit, success, failure)) zero-cost abstractions?
I'm curious whether scope guards add any cost over the naive way, eg: ``` void fun(){ ... scope(success) {bar;} ... } ``` vs: ``` void fun(){ ... if(foo1){ bar; // add this before each return return; } ... bar; return; } ``` For scope(success) and scope(failure), the naive way would anyway involve try/catch statements but what about scope(exit)? Does the zero-cost exception model (zero cost being for non-thrown exceptions) guarantee us that scope(success) has 0 overhead over naive way?
Re: what's the point of function template declarations if they can't be defined?
> It's been my understanding that it's always been illegal to provide a definition for a function that was declared previously unless it was declared in a .di file Compiler has always allowed that: ``` void fun(); void fun(){} ``` (but see details in bug report) > It's useful with stuff like version(Ddoc). I guess you mean `version(StdDdoc)` ? On that note, I see things like this, which are not DRY: ``` version(StdDdoc) string readLink(R)(R link) if (isInputRange!R && !isInfinite!R && isSomeChar!(ElementEncodingType!R) || isConvertibleToString!R); else version(Posix) string readLink(R)(R link) if (isInputRange!R && !isInfinite!R && isSomeChar!(ElementEncodingType!R) || isConvertibleToString!R) ``` Is this pattern used because we want to build DDoc on a not-necessarily Posix system (ie to get a DDoc regardless of which environment)? If so, it seems like an anti-pattern; better options could be: * build platform specific documentation (which actually makes sense, eg a windows user may not want to see Posix-only functions) * add a special compiler flag that overrides predefined builtins (eg Posix) On Wed, Feb 7, 2018 at 11:21 PM, Jonathan M Davis via Digitalmars-d-learnwrote: > On Wednesday, February 07, 2018 13:39:55 Timothee Cour via Digitalmars-d- > learn wrote: >> ``` >> void fun_bad3(T)(T a); // declaration [1] >> void fun_bad3(T)(T a){}; // definition [2] >> void test(){ >> fun_bad3(1); >> } >> ``` >> Error: test_all.fun_bad3 called with argument types (int) matches both: >> main.d(11): test_all.fun_bad3!int.fun_bad3(int a) >> and: >> main.d(12): test_all.fun_bad3!int.fun_bad3(int a) >> >> should [1] be allowed? > > It's useful with stuff like version(Ddoc). > >> compler doens't allow defining it afterwards in >> [2] (unlike function definitions, and, well, modulo this regression >> https://issues.dlang.org/show_bug.cgi?id=18393) > > It's been my understanding that it's always been illegal to provide a > definition for a function that was declared previously unless it was > declared in a .di file, in which case, you're not really both declaring and > defining it, but the .d file is used when the module is compiled, and the > .di file is used by other modules which use that module, so the declaration > and definition are not seen by the same run of the compiler. > > - Jonathan M Davis >
Re: free func "front" is not picked up as a candidate when doing range.front(...)
On Thursday, 8 February 2018 at 07:16:43 UTC, Jonathan M Davis wrote: It would be a disaster if free functions could override member functions. For starters, it would be impossible to call the member function if that were allowed, whereas you can always call a free function by not using UFCS. And in general, it's far more desirable to have member function functions override free functions, because then you can do stuff like have have a range override find if it can provide a more efficient implementation than std.algorithm.find. That could be fixed with a precedence rule though no? Then member find will be preferred over free find. And it won't be impossible to call member functions. Also, in this case where it's an overload, and not an override, it's very clear what should be called isn't it? In the case of an override I "feel" it may indeed be a disaster, but not for the reasons you've stated above though, also not for any reasons I can think of :) Hijacking maybe? But then again, if I have a free function and then decide to make a member function I'm hijacking the free function... hmm. Cheers